Bob Swan
Bob Swan

Reputation: 1

Enabling a setuid cpp program to run a command - "groups" shows the realuser groups instead of effective user

I am trying to write a cpp program that will act as "sudo" for a faceless account. Basically i want the command to be run AS the faceless account rather than as the user invoking the command. I intend to do this by writing a cpp program that i will compile, chown it to the faceless account, and set the setuid bit. This is almost entirely working, but i can't get all the way there because it seems that there are reminents of the realuser that corrupt the results. This is the code block that does the setuid:

    uid_t euid, ruid;

    ruid = getuid();
    euid = geteuid();
    seteuid(ruid);

    int childPid = fork();
    if(childPid == 0){
        seteuid(euid);
        execvp(command, arguments);
    } else {
        wait(childPid);
    }

after compiling the code, chowning it, and setting the setuid bit as the facelsss it looks like this:

[user@home]$ ls -ltr ../bin/.sudo
-rwsr-xr-x 1 cadtools vendor_tools 13224 Feb 21 18:23 ../bin/.sudo
[user@home]$

when i run the code as my username, it correctly reports "whoami" as the faceless account:

[user@home]$ ../bin/.sudo /usr/bin/whoami
cadtools
[user@home]$

but the result of "groups" is not correct. the result of "groups" is the usernames groups, not the faceless accounts:

[user@home]$ ../bin/.sudo /usr/bin/groups
domain users vpn_users linux-admins hw engineering wifi_eng rtm_admins hw_er
[user@home]$ /usr/bin/groups
domain users vpn_users linux-admins hw engineering wifi_eng rtm_admins hw_er
[user@home]$ /usr/bin/groups cadtools
cadtools : domain users vendor_tools engineering hw
[user@home]$

why isnt the execvp() call seeing "everything" as the faceless account?

i've tried with and without the forking and seteuid calls, but the result is the same.

Upvotes: 0

Views: 44

Answers (1)

Bob Swan
Bob Swan

Reputation: 1

i figured it out finally - the trick is setreuid(). this is the code that works now:

uid_t euid;

euid = geteuid();

int parentPid = getpid();

setreuid(euid,euid);

int childPid = fork();
if(childPid == 0){
    setsid();
    setreuid(euid,euid);
    execvp(command, arguments);
} else {
    wait(childPid);
}

Upvotes: 0

Related Questions