Ejemplo n.º 1
0
kauth_cred_t
rump_cred_create(uid_t uid, gid_t gid, size_t ngroups, gid_t *groups)
{
	kauth_cred_t cred;
	int rv;

	cred = kauth_cred_alloc();
	kauth_cred_setuid(cred, uid);
	kauth_cred_seteuid(cred, uid);
	kauth_cred_setsvuid(cred, uid);
	kauth_cred_setgid(cred, gid);
	kauth_cred_setgid(cred, gid);
	kauth_cred_setegid(cred, gid);
	kauth_cred_setsvgid(cred, gid);
	rv = kauth_cred_setgroups(cred, groups, ngroups, 0, UIO_SYSSPACE);
	/* oh this is silly.  and by "this" I mean kauth_cred_setgroups() */
	assert(rv == 0);

	return cred;
}
Ejemplo n.º 2
0
int
do_setresuid(struct lwp *l, uid_t r, uid_t e, uid_t sv, u_int flags)
{
	struct proc *p = l->l_proc;
	kauth_cred_t cred, ncred;

	ncred = kauth_cred_alloc();

	/* Get a write lock on the process credential. */
	proc_crmod_enter();
	cred = p->p_cred;

	/*
	 * Check that the new value is one of the allowed existing values,
	 * or that we have root privilege.
	 */
	if ((r != -1
	    && !((flags & ID_R_EQ_R) && r == kauth_cred_getuid(cred))
	    && !((flags & ID_R_EQ_E) && r == kauth_cred_geteuid(cred))
	    && !((flags & ID_R_EQ_S) && r == kauth_cred_getsvuid(cred))) ||
	    (e != -1
	    && !((flags & ID_E_EQ_R) && e == kauth_cred_getuid(cred))
	    && !((flags & ID_E_EQ_E) && e == kauth_cred_geteuid(cred))
	    && !((flags & ID_E_EQ_S) && e == kauth_cred_getsvuid(cred))) ||
	    (sv != -1
	    && !((flags & ID_S_EQ_R) && sv == kauth_cred_getuid(cred))
	    && !((flags & ID_S_EQ_E) && sv == kauth_cred_geteuid(cred))
	    && !((flags & ID_S_EQ_S) && sv == kauth_cred_getsvuid(cred)))) {
		int error;

		error = kauth_authorize_process(cred, KAUTH_PROCESS_SETID,
		    p, NULL, NULL, NULL);
		if (error != 0) {
		 	proc_crmod_leave(cred, ncred, false);
			return error;
		}
	}

	/* If nothing has changed, short circuit the request */
	if ((r == -1 || r == kauth_cred_getuid(cred))
	    && (e == -1 || e == kauth_cred_geteuid(cred))
	    && (sv == -1 || sv == kauth_cred_getsvuid(cred))) {
		proc_crmod_leave(cred, ncred, false);
		return 0;
	}

	kauth_cred_clone(cred, ncred);

	if (r != -1 && r != kauth_cred_getuid(ncred)) {
		u_long nlwps;

		/* Update count of processes for this user. */
		(void)chgproccnt(kauth_cred_getuid(ncred), -1);
		(void)chgproccnt(r, 1);

		/* The first LWP of a process is excluded. */
		KASSERT(mutex_owned(p->p_lock));
		nlwps = p->p_nlwps - 1;
		(void)chglwpcnt(kauth_cred_getuid(ncred), -nlwps);
		(void)chglwpcnt(r, nlwps);

		kauth_cred_setuid(ncred, r);
	}
	if (sv != -1)
		kauth_cred_setsvuid(ncred, sv);
	if (e != -1)
		kauth_cred_seteuid(ncred, e);

	/* Broadcast our credentials to the process and other LWPs. */
 	proc_crmod_leave(ncred, cred, true);

	return 0;
}