CGI script SUID?


I would like a to make a script that makes it possible for users to change their .forward file through a HTML interface. I have no trouble programming this, but to open the .forward files for write, I need to SUID to the
users UID (or SUID root and then chown the file afterwards). I'm using apache 1.2.5, which doesn't execute
scripts with the SUID bit set. Does anybody know a solution for this? I've looked into the suexec wrapper, but there doesn't seem to be a method to suid to a UID depending on who has logged into the webpage.
Who is Participating?
eckspurtConnect With a Mentor Commented:
Apache does allow you to have suid CGI programs.

You're right that there's nothing ready-made to set the effective user in a CGI suid wrapper, but if the wrapper is suid root, it will be allowed to edit any user's .forward file.  Make sure, of course, that you've restricted access based on user first!

The best thing to do would probably be to edit the suid wrapper to check who the user is authenticated as (which you get as a CGI environment variable), then set the effective user to be that.  You still run the wrapper suid root (only root can change the effective user), but it slightly limits the potential damage a malicious user could do.  

You didn't say what language you're writing your CGI in, but it would be best to do the whole thing in C or Safe Perl so you can suid only the file that contains the function you need the effective user changed for (writing a user's .forward file).

One simple way to deal with the above problem is to create a special group and change all the .forward file to rw-rw---- so any scripts with that GID could edit that file. But it has a potential problem if the owner of the .forward file change the permission to 600 again. I've looked at the suexec wrapper, the docs says it must be install as root and have the SUID bit set to on. Unfortunately, it doesn't allow you  to modify anything not under the DocumentRoot dir. Another solution would be adding the changes to a file
with the format "user:email addr" then every 5, 10 minutes a cron job as root to read that file and edit the user's .forward file accordingly.

Minh Lai
alexbikAuthor Commented:

I've looked into a group-based solution, but this is not acceptable to me.
The problem is that a user can also put a .forward in his homedir through
ftp or telnet. It is owned by the user, goup users. In this way I cannot access
the file for write anymore from my script if I would do It on a group basis.
I cannot use the group 'users' for this purpose, or all users will be able toe
change other users' .forward files.

The thought of running a cron job processing the files once every few minutes
crossed my mind, but it's a bit messy I would like the changes to be processed
right away.

If no one comes up with a better solution I'll give you the points.

alexbikAuthor Commented:

I'm writing the script in perl. If I make the script SUID root, I get an 500.
Here's what the logfile says:

Can't do setuid
[Wed Apr  1 19:40:06 1998] access to /var/http/cgi-bin/ failed for, reason: Premature end of script headers

Apearantly Apache refuses to run suid perlscripts. It may be possible to do it in C though, but that gives me the following problem: I don't want to write the whole script in C. If I write only the part that creates the .forward in C, I need to pass the content, the username and the filename (or only the username and the content) on to the C code. There's a potential security risk, because I have no way of checking that the script is started by the CGI script (meaning the user is already authenticated).  Or is there? (I can get around in perl, but I'm really no C programmer).

alexbikAuthor Commented:

I've come up with a solution to the problem. A friend of mine wrote a C program
that reads the CGI data, compares the username I pass him from my perl script
with the username in the REMOTE_USER environment var, writes the file,
and chowns it to the users' UID. Since this is C code, it can be executed SUID.
The program is owned by root.www, permissions 4550. In this way it can only be
executed by the webserver. Since it is in a .htaccess secured directory, only
authenticated users can use it. The parameters passed from the HTML form are
checked against the environment var, to prevent misuse of the program.

Thanks anyway.

Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.

All Courses

From novice to tech pro — start learning today.