diff options
author | Rich Felker <dalias@aerifal.cx> | 2011-07-30 08:19:31 -0400 |
---|---|---|
committer | Rich Felker <dalias@aerifal.cx> | 2011-07-30 08:19:31 -0400 |
commit | 544ee752cd38febfa3aa3798b4dfb6fabd13846b (patch) | |
tree | 5367d3f9653484d0498279b87630e8ddb7e084ed /src/unistd | |
parent | dba68bf98fc708cea4c478278c889fc7ad802b00 (diff) | |
download | musl-544ee752cd38febfa3aa3798b4dfb6fabd13846b.zip musl-544ee752cd38febfa3aa3798b4dfb6fabd13846b.tar.gz musl-544ee752cd38febfa3aa3798b4dfb6fabd13846b.tar.bz2 |
fix some bugs in setxid and update setrlimit to use __synccall
setrlimit is supposed to be per-process, not per-thread, but again
linux gets it wrong. work around this in userspace. not only is it
needed for correctness; setxid also depends on the resource limits for
all threads being the same to avoid situations where temporarily
unlimiting the limit succeeds in some threads but fails in others.
Diffstat (limited to 'src/unistd')
-rw-r--r-- | src/unistd/setxid.c | 14 |
1 files changed, 6 insertions, 8 deletions
diff --git a/src/unistd/setxid.c b/src/unistd/setxid.c index d3bfaf6..2f651a1 100644 --- a/src/unistd/setxid.c +++ b/src/unistd/setxid.c @@ -11,6 +11,8 @@ struct ctx { /* We jump through hoops to eliminate the possibility of partial failures. */ +int __setrlimit(int, const struct rlimit *); + static void do_setxid(void *p) { struct ctx *c = p; @@ -18,17 +20,13 @@ static void do_setxid(void *p) if (c->rlim && c->id >= 0 && c->id != getuid()) { struct rlimit inf = { RLIM_INFINITY, RLIM_INFINITY }, old; getrlimit(RLIMIT_NPROC, &old); - if (setrlimit(RLIMIT_NPROC, &inf) && libc.threads_minus_1) { - c->err = errno; + if ((c->err = -__setrlimit(RLIMIT_NPROC, &inf)) && libc.threads_minus_1) return; - } - if (__syscall(c->nr, c->id, c->eid, c->sid)) - c->err = errno; - setrlimit(RLIMIT_NPROC, &old); + c->err = -__syscall(c->nr, c->id, c->eid, c->sid); + __setrlimit(RLIMIT_NPROC, &old); return; } - if (__syscall(c->nr, c->id, c->eid, c->sid)) - c->err = errno; + c->err = -__syscall(c->nr, c->id, c->eid, c->sid); } int __setxid(int nr, int id, int eid, int sid) |