How to lose extra groups? setgroups()?

Brian Dowling (
Mon, 03 Mar 1997 02:58:54 -0500

Hey folks,

I'm a little stumped, and I'm wondering if you can help with this.

I'm trying to figure out if it is possible for a non-priveleged
set-uid program to lose the "extra groups" of the caller.

You guys fixed that saved-set user id security hole, so a program can
call setreuid(geteuid(), geteuid()) to drop UID privilege of the
caller, but I can't see any way to get rid of extra groups. I did
figure out that I could also make the program setgid to set the
"default group" to be what I want, but this still leaves the
additional groups (which included at least the caller's default

I found a manpage at
-- although I have no idea what system this is referring to, it mentions
that a _any_ program can delete groups, even non-privleged ones. But
looking at the kernel source, this is not true in linux. If it was, I
would expect I would be able to call setgroups with just the groups I
want (a subset of what the program currently has).

According to the manpages for various commercial OS' at none of them
provide the above mentioned functionality via setgroups(). But I
don't see any reason why setgroups shouldn't be used this way??? (The
only case I could think of is if groups were used to list negative
access. i.e. a program checked if you belonged to the 'no-access'
group itself before allowing something, but I highly doubt anyone uses
groups in this way. Most systems don't even use groups for what they
ARE good for.)

I was also wondering if intigroups() had the capability to "reset" the
groups of an unprivileged process to it's default list, essentially
what I want to do, but since this is a c library function, I realize
this is not possible.

Anyways, if this is not currently possible, I have an suggestion.
Does the Sticky bit (01000) have any special meaning for files? The
reason ask, is that I was thinking this bit could be used for the
purpose of saying "This program should run with, and only with the
Setuid & Setgid permissions as specified." i.e. when run, the kernel
would initialize the extraneous groups to contain just the setGID one.
(I suppose it could also call initgroups() based on the Setuid, but
that would be behavior might be considered questionable.)

I guess I could also modify sys_setgroups() to "delete groups" for
users, as the constitution manpage above suggests, but I'd rather have
the solution to this become "linux standard," rather than a private

Just in case someone might suggest it. I realize that I could do this
by writing a secure program that is setuid root. However I don't want
to do that. Especially since I recently found a security hole (a root
compromise) in what appeared to be a very simple wrapper program.

Brian Dowling