1

[EDIT: Revisiting this question and seeing it is still wrongly marked as a duplicate] The following question on SE is not a duplicate as it asks about executing bash with the suid bit, which is a special case and does not work at all: Setuid bit seems to have no effect on bash The first difference is that in my example I execute whoami, not bash. The second difference is that it actually works as expected on Ubuntu, but not on SuSE.

Suid bit works fine on my PC running Ubuntu, but not on a SLES test instance. The nosuid flag is not set on the mounted xfs file system on the SLES machine. ls shows that ony my machine and the SLE Server, the same permissions are set for the executable. So why does the executable still run as the current user instead of as the owner?

execsudo.c:

#include <stdio.h>
#include <stdlib.h>

int main(int argc,char *argv[]) {
    system(argv[1]);
    return 0;
}

bash:

gcc -o setuid-test execsudo.c ;
sudo chown nobody ./setuid-test;
sudo chmod +s ./setuid-test;
./setuid-test "whoami" 
# Outputs current user instead of nobody

[EDIT 2] I still have not worked out the problem, but I suppose it might be because the SuSE machine is a VM. A workaround might be to configure this behaviour via /etc/sudoers instead.

phobic
  • 131
  • You did the chown after the chmod ? That might cause the setuid bit to be removed... – Stephen Harris Aug 19 '16 at 15:11
  • @StephenHarris: Right, this is not the problem though. Just to be sure, I ran the test again with the same result. Also, I compared the permissions with my PC version, with ls; the bit is set correctly. Thanks for pointing out the mistake, I will correct my post. – phobic Aug 19 '16 at 15:53
  • 2
    What happens if you put a setuid(geteuid()) call before the system()? Or just a printf("%d\n",geteuid()); call? – Stephen Harris Aug 19 '16 at 16:01
  • @StephenHarris: This prints the id of nobody in both cases. But whoami still shows the the current user. – phobic Aug 19 '16 at 16:35
  • So that shows the setuid is working. The problem is occuring afterwards. What happens if you run id instead of whoami ? – Stephen Harris Aug 19 '16 at 16:46
  • @StephenHarris: id also shows the current user. id -u differs from the output of geteuid. – phobic Aug 19 '16 at 17:38
  • I called ./setuid-test "setuid-test id"; Now it prints getuid of 'nobody' twice and then outputs the id of the current user. So it works with some programs, but maybe not shell builtins? Edit: No, calling /usr/bin/whoami does not change the result. – phobic Aug 19 '16 at 17:41
  • id typically isn't a builtin (/usr/bin/id). Makes me wonder if there's some other layer (SELinux, Apparmour or SLES equiv) that's not allowing transitions in some cases. confusing – Stephen Harris Aug 19 '16 at 17:45
  • Bash 4.3.30 on Debian doesn't seem to exhibit that permission dropping if it's started as sh (like system(3)) does. I don't know if that's a distro-specific change, though. And no, I didn't run dash, but a renamed, setuid copy of bash. – ilkkachu Aug 21 '16 at 13:29
  • You're right. It's not a duplicate to the one marked, but that would make it off-topic because it's a programming error simply because you didn't call setuid() in your program. I'll vote to reopen it to remove the duplicate flag so it can be flagged off-topic. – Julie Pelletier Aug 22 '16 at 16:25
  • @Julie Pelletier: If you follow the comments, you can see that I tried calling setuid to no effect. Also, as mentioned in my post calling the function is not necessary on my Ubuntu machine. Apart from that, if you can point out a programming error I can't see, please do so. – phobic Aug 23 '16 at 07:11

1 Answers1

0

The setuid may "work", but is easily detected and undone later. I compared this with a similarly-intentioned program sue, which I use locally in an alternate account dickey (naming the program dickey).

On my Debian 7 system, I get this output (yours is "foo"):

$ ./foo id;dickey id
uid=1001(tom) gid=100(users) euid=1006(dickey) egid=50(staff) groups=100(users),27(sudo)
uid=1006(dickey) gid=100(users) groups=100(users),27(sudo)

On my OpenSUSE 13, I get something different:

$ ./foo id;dickey id
uid=1000(thomas) gid=100(users) groups=100(users),10(wheel)
uid=1003(dickey) gid=100(users) groups=100(users),10(wheel)

The reason for the difference is that your program does not set its real uid/gid values to match the effective uid/gid values, and a helpful program (perhaps apparmor) is stripping off the unwanted permissions.

This still isn't a perfect solution (I have a to-do item for CentOS 7 where another helpful program interferes with setuid programs). But it should point you in the right direction.

Further reading:

Thomas Dickey
  • 76,765