Re: SetUID & Operation not permitted

From: Robert Newson (ReapNewsB_at_bullet3.fsnet.oc.ku)
Date: 09/18/05

Date: Sun, 18 Sep 2005 08:35:45 GMT

Unruh wrote:

> AFAIK just because you make a program suid does not mean that it runs as
> say root. You need to actually change the euid to root in this case within
> the program.

Nope...that is exactly what the suid bit does: it sets the effective uid of
the process. As a test, try the following:

$ su
# cd /tmp
# cat > testuid.c
main ()
    printf(" uid = %d\neuid = %d\n", getuid(), geteuid());
^D# make testuid
cc testuid.c -o testuid
# chmod 04711 testuid
# ls -lF testuid
-rws--x--x 1 root root 11950 Sep 18 09:17 testuid*
# ./testuid
  uid = 0
euid = 0
# exit
$ /tmp/testuid
  uid = 1000
euid = 0

> eg, here is a fragment from one of my wrappers
> uid=getuid();
> if ( (pwd = getpwuid(uid))== (struct passwd *)0 )
> exit(1);

> setuid((uid_t)0);

if geteuid() == root, then this will set both uid and euid to root (making
you properly root), ie afterwards, getuid() == root && geteuid() == root:

$ man setuid
        setuid sets the effective user ID of the current process.
        If the effective userid of the caller is root, the real
        and saved user ID's are also set.
        If the user is root or the program is setuid root, special
        care must be taken. The setuid function checks the effec­-
        tive uid of the caller and if it is the superuser, all
        process related user ID's are set to uid. After this has
        occurred, it is impossible for the program to regain root

> execle("/usr/local/bin/net","/usr/local/bin/net",argv[1],(char *)0,trusted_env);