diff options
| author | Ingo Molnar <mingo@elte.hu> | 2009-03-13 02:14:25 +0100 | 
|---|---|---|
| committer | Ingo Molnar <mingo@elte.hu> | 2009-03-13 02:14:25 +0100 | 
| commit | 25d500067d5a666d1336598d1b324793554e5496 (patch) | |
| tree | 3402308c4c69a66d02ce55f5c165e242fad2a8a9 /kernel/sys.c | |
| parent | 0b13fda1e0936b3d64c4c407f183d33fa6bd2ad4 (diff) | |
| parent | 9ead64974b05501bbac0d63a47c99fa786d064ba (diff) | |
Merge branch 'linus' into core/ipi
Diffstat (limited to 'kernel/sys.c')
| -rw-r--r-- | kernel/sys.c | 31 | 
1 files changed, 20 insertions, 11 deletions
| diff --git a/kernel/sys.c b/kernel/sys.c index f145c415bc16..37f458e6882a 100644 --- a/kernel/sys.c +++ b/kernel/sys.c @@ -559,7 +559,7 @@ error:  	abort_creds(new);  	return retval;  } -   +  /*   * change the user struct in a credentials set to match the new UID   */ @@ -571,6 +571,11 @@ static int set_user(struct cred *new)  	if (!new_user)  		return -EAGAIN; +	if (!task_can_switch_user(new_user, current)) { +		free_uid(new_user); +		return -EINVAL; +	} +  	if (atomic_read(&new_user->processes) >=  				current->signal->rlim[RLIMIT_NPROC].rlim_cur &&  			new_user != INIT_USER) { @@ -631,10 +636,11 @@ SYSCALL_DEFINE2(setreuid, uid_t, ruid, uid_t, euid)  			goto error;  	} -	retval = -EAGAIN; -	if (new->uid != old->uid && set_user(new) < 0) -		goto error; - +	if (new->uid != old->uid) { +		retval = set_user(new); +		if (retval < 0) +			goto error; +	}  	if (ruid != (uid_t) -1 ||  	    (euid != (uid_t) -1 && euid != old->uid))  		new->suid = new->euid; @@ -680,9 +686,10 @@ SYSCALL_DEFINE1(setuid, uid_t, uid)  	retval = -EPERM;  	if (capable(CAP_SETUID)) {  		new->suid = new->uid = uid; -		if (uid != old->uid && set_user(new) < 0) { -			retval = -EAGAIN; -			goto error; +		if (uid != old->uid) { +			retval = set_user(new); +			if (retval < 0) +				goto error;  		}  	} else if (uid != old->uid && uid != new->suid) {  		goto error; @@ -734,11 +741,13 @@ SYSCALL_DEFINE3(setresuid, uid_t, ruid, uid_t, euid, uid_t, suid)  			goto error;  	} -	retval = -EAGAIN;  	if (ruid != (uid_t) -1) {  		new->uid = ruid; -		if (ruid != old->uid && set_user(new) < 0) -			goto error; +		if (ruid != old->uid) { +			retval = set_user(new); +			if (retval < 0) +				goto error; +		}  	}  	if (euid != (uid_t) -1)  		new->euid = euid; | 
