What are the things one has to take care of when writing a suid root
I've found a few points, and I'm wondering if other people could
add some more.
- Don't use buffers which could be overrun by the user; use dynamic
memory or truncuate his input, if necessary. Using gets() or
scanf("%s") is a sure way to ruin.
- Don't use functions which rely on the user's environment. Invoking
another program via system(), popen() or exec?p without explicitly
setting your own environment including PATH and IFS is a no-no,
as is using the tmpnam() function, which rely on the user's
- Don't write to files if the user has write permission in any
of the directories leading up to it, if you need to open the
file to write to it. Writing to stdout and stderr should
be ok (IS THAT RIGHT?), as should be reading from stdin.
- Don't trust filenames supplied by the user for either reading or
writing. Using access() is not enough, because of possible race
conditions and symbolic links. (The only solution I've found so far
is to fork off a child, which does a setgid(getgid());
setuid(getuid());, then opens the file and reads from/ writes to it,
communicating with its parent with a pipe. This is far from elegant,
- Check for every failed function call, and abort if necessary.
The joy of engineering is to find a straight line on a double