Giant Pushdown. Saved the worst P4 tree breakage for last.
reboot() getpriority() setpriority() rtprio() osetrlimit() ogetrlimit() setrlimit() getrlimit() getrusage() getpid() getppid() getpgrp() getpgid() getsid() getgid() getegid() getgroups() setsid() setpgid() setuid() seteuid() setgid() setegid() setgroups() setreuid() setregid() setresuid() setresgid() getresuid() getresgid () __setugid() getlogin() setlogin() modnext() modfnext() modstat() modfind() kldload() kldunload() kldfind() kldnext() kldstat() kldfirstmod() kldsym() getdtablesize() dup2() dup() fcntl() close() ofstat() fstat() nfsstat() fpathconf() flock()
This commit is contained in:
parent
e619430f32
commit
835a82ee2d
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=82749
@ -116,6 +116,9 @@ struct getdtablesize_args {
|
||||
int dummy;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getdtablesize(p, uap)
|
||||
@ -123,8 +126,10 @@ getdtablesize(p, uap)
|
||||
struct getdtablesize_args *uap;
|
||||
{
|
||||
|
||||
mtx_lock(&Giant);
|
||||
p->p_retval[0] =
|
||||
min((int)p->p_rlimit[RLIMIT_NOFILE].rlim_cur, maxfilesperproc);
|
||||
mtx_unlock(&Giant);
|
||||
return (0);
|
||||
}
|
||||
|
||||
@ -140,6 +145,9 @@ struct dup2_args {
|
||||
u_int to;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
dup2(p, uap)
|
||||
@ -150,20 +158,23 @@ dup2(p, uap)
|
||||
register u_int old = uap->from, new = uap->to;
|
||||
int i, error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
retry:
|
||||
if (old >= fdp->fd_nfiles ||
|
||||
fdp->fd_ofiles[old] == NULL ||
|
||||
new >= p->p_rlimit[RLIMIT_NOFILE].rlim_cur ||
|
||||
new >= maxfilesperproc) {
|
||||
return (EBADF);
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
if (old == new) {
|
||||
p->p_retval[0] = new;
|
||||
return (0);
|
||||
error = 0;
|
||||
goto done2;
|
||||
}
|
||||
if (new >= fdp->fd_nfiles) {
|
||||
if ((error = fdalloc(p, new, &i)))
|
||||
return (error);
|
||||
goto done2;
|
||||
if (new != i)
|
||||
panic("dup2: fdalloc");
|
||||
/*
|
||||
@ -171,7 +182,10 @@ dup2(p, uap)
|
||||
*/
|
||||
goto retry;
|
||||
}
|
||||
return (do_dup(fdp, (int)old, (int)new, p->p_retval, p));
|
||||
error = do_dup(fdp, (int)old, (int)new, p->p_retval, p);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return(error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -182,6 +196,9 @@ struct dup_args {
|
||||
u_int fd;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
dup(p, uap)
|
||||
@ -192,13 +209,19 @@ dup(p, uap)
|
||||
u_int old;
|
||||
int new, error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
old = uap->fd;
|
||||
fdp = p->p_fd;
|
||||
if (old >= fdp->fd_nfiles || fdp->fd_ofiles[old] == NULL)
|
||||
return (EBADF);
|
||||
if (old >= fdp->fd_nfiles || fdp->fd_ofiles[old] == NULL) {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
if ((error = fdalloc(p, 0, &new)))
|
||||
return (error);
|
||||
return (do_dup(fdp, (int)old, new, p->p_retval, p));
|
||||
goto done2;
|
||||
error = do_dup(fdp, (int)old, new, p->p_retval, p);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -211,46 +234,57 @@ struct fcntl_args {
|
||||
long arg;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
fcntl(p, uap)
|
||||
struct proc *p;
|
||||
register struct fcntl_args *uap;
|
||||
{
|
||||
register struct filedesc *fdp = p->p_fd;
|
||||
register struct filedesc *fdp;
|
||||
register struct file *fp;
|
||||
register char *pop;
|
||||
struct vnode *vp;
|
||||
int i, tmp, error, flg = F_POSIX;
|
||||
int i, tmp, error = 0, flg = F_POSIX;
|
||||
struct flock fl;
|
||||
u_int newmin;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
fdp = p->p_fd;
|
||||
if ((unsigned)uap->fd >= fdp->fd_nfiles ||
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL)
|
||||
return (EBADF);
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL) {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
pop = &fdp->fd_ofileflags[uap->fd];
|
||||
|
||||
switch (uap->cmd) {
|
||||
case F_DUPFD:
|
||||
newmin = uap->arg;
|
||||
if (newmin >= p->p_rlimit[RLIMIT_NOFILE].rlim_cur ||
|
||||
newmin >= maxfilesperproc)
|
||||
return (EINVAL);
|
||||
newmin >= maxfilesperproc) {
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
if ((error = fdalloc(p, newmin, &i)))
|
||||
return (error);
|
||||
return (do_dup(fdp, uap->fd, i, p->p_retval, p));
|
||||
break;
|
||||
error = do_dup(fdp, uap->fd, i, p->p_retval, p);
|
||||
break;
|
||||
|
||||
case F_GETFD:
|
||||
p->p_retval[0] = *pop & 1;
|
||||
return (0);
|
||||
break;
|
||||
|
||||
case F_SETFD:
|
||||
*pop = (*pop &~ 1) | (uap->arg & 1);
|
||||
return (0);
|
||||
break;
|
||||
|
||||
case F_GETFL:
|
||||
p->p_retval[0] = OFLAGS(fp->f_flag);
|
||||
return (0);
|
||||
break;
|
||||
|
||||
case F_SETFL:
|
||||
fhold(fp);
|
||||
@ -260,39 +294,41 @@ fcntl(p, uap)
|
||||
error = fo_ioctl(fp, FIONBIO, (caddr_t)&tmp, p);
|
||||
if (error) {
|
||||
fdrop(fp, p);
|
||||
return (error);
|
||||
break;
|
||||
}
|
||||
tmp = fp->f_flag & FASYNC;
|
||||
error = fo_ioctl(fp, FIOASYNC, (caddr_t)&tmp, p);
|
||||
if (!error) {
|
||||
fdrop(fp, p);
|
||||
return (0);
|
||||
break;
|
||||
}
|
||||
fp->f_flag &= ~FNONBLOCK;
|
||||
tmp = 0;
|
||||
(void)fo_ioctl(fp, FIONBIO, (caddr_t)&tmp, p);
|
||||
fdrop(fp, p);
|
||||
return (error);
|
||||
break;
|
||||
|
||||
case F_GETOWN:
|
||||
fhold(fp);
|
||||
error = fo_ioctl(fp, FIOGETOWN, (caddr_t)p->p_retval, p);
|
||||
fdrop(fp, p);
|
||||
return(error);
|
||||
break;
|
||||
|
||||
case F_SETOWN:
|
||||
fhold(fp);
|
||||
error = fo_ioctl(fp, FIOSETOWN, (caddr_t)&uap->arg, p);
|
||||
fdrop(fp, p);
|
||||
return(error);
|
||||
break;
|
||||
|
||||
case F_SETLKW:
|
||||
flg |= F_WAIT;
|
||||
/* Fall into F_SETLK */
|
||||
|
||||
case F_SETLK:
|
||||
if (fp->f_type != DTYPE_VNODE)
|
||||
return (EBADF);
|
||||
if (fp->f_type != DTYPE_VNODE) {
|
||||
error = EBADF;
|
||||
break;
|
||||
}
|
||||
vp = (struct vnode *)fp->f_data;
|
||||
|
||||
/*
|
||||
@ -304,14 +340,15 @@ fcntl(p, uap)
|
||||
sizeof(fl));
|
||||
if (error) {
|
||||
fdrop(fp, p);
|
||||
return (error);
|
||||
break;
|
||||
}
|
||||
if (fl.l_whence == SEEK_CUR) {
|
||||
if (fp->f_offset < 0 ||
|
||||
(fl.l_start > 0 &&
|
||||
fp->f_offset > OFF_MAX - fl.l_start)) {
|
||||
fdrop(fp, p);
|
||||
return (EOVERFLOW);
|
||||
error = EOVERFLOW;
|
||||
break;
|
||||
}
|
||||
fl.l_start += fp->f_offset;
|
||||
}
|
||||
@ -344,11 +381,12 @@ fcntl(p, uap)
|
||||
break;
|
||||
}
|
||||
fdrop(fp, p);
|
||||
return(error);
|
||||
|
||||
break;
|
||||
case F_GETLK:
|
||||
if (fp->f_type != DTYPE_VNODE)
|
||||
return (EBADF);
|
||||
if (fp->f_type != DTYPE_VNODE) {
|
||||
error = EBADF;
|
||||
break;
|
||||
}
|
||||
vp = (struct vnode *)fp->f_data;
|
||||
/*
|
||||
* copyin/lockop may block
|
||||
@ -359,12 +397,13 @@ fcntl(p, uap)
|
||||
sizeof(fl));
|
||||
if (error) {
|
||||
fdrop(fp, p);
|
||||
return (error);
|
||||
break;
|
||||
}
|
||||
if (fl.l_type != F_RDLCK && fl.l_type != F_WRLCK &&
|
||||
fl.l_type != F_UNLCK) {
|
||||
fdrop(fp, p);
|
||||
return (EINVAL);
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
if (fl.l_whence == SEEK_CUR) {
|
||||
if ((fl.l_start > 0 &&
|
||||
@ -372,7 +411,8 @@ fcntl(p, uap)
|
||||
(fl.l_start < 0 &&
|
||||
fp->f_offset < OFF_MIN - fl.l_start)) {
|
||||
fdrop(fp, p);
|
||||
return (EOVERFLOW);
|
||||
error = EOVERFLOW;
|
||||
break;
|
||||
}
|
||||
fl.l_start += fp->f_offset;
|
||||
}
|
||||
@ -383,11 +423,14 @@ fcntl(p, uap)
|
||||
error = copyout((caddr_t)&fl,
|
||||
(caddr_t)(intptr_t)uap->arg, sizeof(fl));
|
||||
}
|
||||
return(error);
|
||||
break;
|
||||
default:
|
||||
return (EINVAL);
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
/* NOTREACHED */
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -568,19 +611,27 @@ struct close_args {
|
||||
int fd;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
close(p, uap)
|
||||
struct proc *p;
|
||||
struct close_args *uap;
|
||||
{
|
||||
register struct filedesc *fdp = p->p_fd;
|
||||
register struct filedesc *fdp;
|
||||
register struct file *fp;
|
||||
register int fd = uap->fd;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
fdp = p->p_fd;
|
||||
if ((unsigned)fd >= fdp->fd_nfiles ||
|
||||
(fp = fdp->fd_ofiles[fd]) == NULL)
|
||||
return (EBADF);
|
||||
(fp = fdp->fd_ofiles[fd]) == NULL) {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
#if 0
|
||||
if (fdp->fd_ofileflags[fd] & UF_MAPPED)
|
||||
(void) munmapfd(p, fd);
|
||||
@ -598,7 +649,10 @@ close(p, uap)
|
||||
fdp->fd_freefile = fd;
|
||||
if (fd < fdp->fd_knlistsize)
|
||||
knote_fdclose(p, fd);
|
||||
return (closef(fp, p));
|
||||
error = closef(fp, p);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return(error);
|
||||
}
|
||||
|
||||
#if defined(COMPAT_43) || defined(COMPAT_SUNOS)
|
||||
@ -611,6 +665,9 @@ struct ofstat_args {
|
||||
struct ostat *sb;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
ofstat(p, uap)
|
||||
@ -623,9 +680,13 @@ ofstat(p, uap)
|
||||
struct ostat oub;
|
||||
int error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if ((unsigned)uap->fd >= fdp->fd_nfiles ||
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL)
|
||||
return (EBADF);
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL) {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
fhold(fp);
|
||||
error = fo_stat(fp, &ub, p);
|
||||
if (error == 0) {
|
||||
@ -633,6 +694,8 @@ ofstat(p, uap)
|
||||
error = copyout((caddr_t)&oub, (caddr_t)uap->sb, sizeof (oub));
|
||||
}
|
||||
fdrop(fp, p);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
#endif /* COMPAT_43 || COMPAT_SUNOS */
|
||||
@ -646,25 +709,35 @@ struct fstat_args {
|
||||
struct stat *sb;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
fstat(p, uap)
|
||||
struct proc *p;
|
||||
register struct fstat_args *uap;
|
||||
{
|
||||
register struct filedesc *fdp = p->p_fd;
|
||||
register struct filedesc *fdp;
|
||||
register struct file *fp;
|
||||
struct stat ub;
|
||||
int error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
fdp = p->p_fd;
|
||||
|
||||
if ((unsigned)uap->fd >= fdp->fd_nfiles ||
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL)
|
||||
return (EBADF);
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL) {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
fhold(fp);
|
||||
error = fo_stat(fp, &ub, p);
|
||||
if (error == 0)
|
||||
error = copyout((caddr_t)&ub, (caddr_t)uap->sb, sizeof (ub));
|
||||
fdrop(fp, p);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
@ -677,21 +750,29 @@ struct nfstat_args {
|
||||
struct nstat *sb;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
nfstat(p, uap)
|
||||
struct proc *p;
|
||||
register struct nfstat_args *uap;
|
||||
{
|
||||
register struct filedesc *fdp = p->p_fd;
|
||||
register struct filedesc *fdp;
|
||||
register struct file *fp;
|
||||
struct stat ub;
|
||||
struct nstat nub;
|
||||
int error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
fdp = p->p_fd;
|
||||
if ((unsigned)uap->fd >= fdp->fd_nfiles ||
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL)
|
||||
return (EBADF);
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL) {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
fhold(fp);
|
||||
error = fo_stat(fp, &ub, p);
|
||||
if (error == 0) {
|
||||
@ -699,6 +780,8 @@ nfstat(p, uap)
|
||||
error = copyout((caddr_t)&nub, (caddr_t)uap->sb, sizeof (nub));
|
||||
}
|
||||
fdrop(fp, p);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
@ -711,28 +794,38 @@ struct fpathconf_args {
|
||||
int name;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
fpathconf(p, uap)
|
||||
struct proc *p;
|
||||
register struct fpathconf_args *uap;
|
||||
{
|
||||
struct filedesc *fdp = p->p_fd;
|
||||
struct filedesc *fdp;
|
||||
struct file *fp;
|
||||
struct vnode *vp;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
fdp = p->p_fd;
|
||||
|
||||
if ((unsigned)uap->fd >= fdp->fd_nfiles ||
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL)
|
||||
return (EBADF);
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL) {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
|
||||
fhold(fp);
|
||||
|
||||
switch (fp->f_type) {
|
||||
case DTYPE_PIPE:
|
||||
case DTYPE_SOCKET:
|
||||
if (uap->name != _PC_PIPE_BUF)
|
||||
return (EINVAL);
|
||||
if (uap->name != _PC_PIPE_BUF) {
|
||||
error = EINVAL;
|
||||
goto done2;
|
||||
}
|
||||
p->p_retval[0] = PIPE_BUF;
|
||||
error = 0;
|
||||
break;
|
||||
@ -746,6 +839,8 @@ fpathconf(p, uap)
|
||||
break;
|
||||
}
|
||||
fdrop(fp, p);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return(error);
|
||||
}
|
||||
|
||||
@ -1274,6 +1369,9 @@ struct flock_args {
|
||||
int how;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
flock(p, uap)
|
||||
@ -1284,12 +1382,19 @@ flock(p, uap)
|
||||
register struct file *fp;
|
||||
struct vnode *vp;
|
||||
struct flock lf;
|
||||
int error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if ((unsigned)uap->fd >= fdp->fd_nfiles ||
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL)
|
||||
return (EBADF);
|
||||
if (fp->f_type != DTYPE_VNODE)
|
||||
return (EOPNOTSUPP);
|
||||
(fp = fdp->fd_ofiles[uap->fd]) == NULL) {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
if (fp->f_type != DTYPE_VNODE) {
|
||||
error = EOPNOTSUPP;
|
||||
goto done2;
|
||||
}
|
||||
vp = (struct vnode *)fp->f_data;
|
||||
lf.l_whence = SEEK_SET;
|
||||
lf.l_start = 0;
|
||||
@ -1297,18 +1402,25 @@ flock(p, uap)
|
||||
if (uap->how & LOCK_UN) {
|
||||
lf.l_type = F_UNLCK;
|
||||
fp->f_flag &= ~FHASLOCK;
|
||||
return (VOP_ADVLOCK(vp, (caddr_t)fp, F_UNLCK, &lf, F_FLOCK));
|
||||
error = VOP_ADVLOCK(vp, (caddr_t)fp, F_UNLCK, &lf, F_FLOCK);
|
||||
goto done2;
|
||||
}
|
||||
if (uap->how & LOCK_EX)
|
||||
lf.l_type = F_WRLCK;
|
||||
else if (uap->how & LOCK_SH)
|
||||
lf.l_type = F_RDLCK;
|
||||
else
|
||||
return (EBADF);
|
||||
else {
|
||||
error = EBADF;
|
||||
goto done2;
|
||||
}
|
||||
fp->f_flag |= FHASLOCK;
|
||||
if (uap->how & LOCK_NB)
|
||||
return (VOP_ADVLOCK(vp, (caddr_t)fp, F_SETLK, &lf, F_FLOCK));
|
||||
return (VOP_ADVLOCK(vp, (caddr_t)fp, F_SETLK, &lf, F_FLOCK|F_WAIT));
|
||||
error = VOP_ADVLOCK(vp, (caddr_t)fp, F_SETLK, &lf, F_FLOCK);
|
||||
else
|
||||
error = VOP_ADVLOCK(vp, (caddr_t)fp, F_SETLK, &lf, F_FLOCK|F_WAIT);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -36,6 +36,7 @@
|
||||
#include <sys/sysent.h>
|
||||
#include <sys/proc.h>
|
||||
#include <sys/lock.h>
|
||||
#include <sys/mutex.h>
|
||||
#include <sys/module.h>
|
||||
#include <sys/linker.h>
|
||||
#include <sys/fcntl.h>
|
||||
@ -692,11 +693,14 @@ linker_ddb_symbol_values(c_linker_sym_t sym, linker_symval_t *symval)
|
||||
/*
|
||||
* Syscalls.
|
||||
*/
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
kldload(struct proc* p, struct kldload_args* uap)
|
||||
{
|
||||
char* pathname, *realpath;
|
||||
char *pathname = NULL;
|
||||
char *realpath = NULL;
|
||||
const char *filename;
|
||||
linker_file_t lf;
|
||||
int error = 0;
|
||||
@ -706,10 +710,11 @@ kldload(struct proc* p, struct kldload_args* uap)
|
||||
if (securelevel > 0) /* redundant, but that's OK */
|
||||
return EPERM;
|
||||
|
||||
if ((error = suser(p)) != 0)
|
||||
return error;
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if ((error = suser(p)) != 0)
|
||||
goto out;
|
||||
|
||||
realpath = NULL;
|
||||
pathname = malloc(MAXPATHLEN, M_TEMP, M_WAITOK);
|
||||
if ((error = copyinstr(SCARG(uap, file), pathname, MAXPATHLEN, NULL)) != 0)
|
||||
goto out;
|
||||
@ -737,9 +742,13 @@ kldload(struct proc* p, struct kldload_args* uap)
|
||||
free(pathname, M_TEMP);
|
||||
if (realpath)
|
||||
free(realpath, M_LINKER);
|
||||
return error;
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
kldunload(struct proc* p, struct kldunload_args* uap)
|
||||
{
|
||||
@ -749,8 +758,10 @@ kldunload(struct proc* p, struct kldunload_args* uap)
|
||||
if (securelevel > 0) /* redundant, but that's OK */
|
||||
return EPERM;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if ((error = suser(p)) != 0)
|
||||
return error;
|
||||
goto out;
|
||||
|
||||
lf = linker_find_file_by_id(SCARG(uap, fileid));
|
||||
if (lf) {
|
||||
@ -764,13 +775,17 @@ kldunload(struct proc* p, struct kldunload_args* uap)
|
||||
error = linker_file_unload(lf);
|
||||
if (error)
|
||||
lf->userrefs++;
|
||||
} else
|
||||
} else {
|
||||
error = ENOENT;
|
||||
|
||||
}
|
||||
out:
|
||||
return error;
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
kldfind(struct proc* p, struct kldfind_args* uap)
|
||||
{
|
||||
@ -779,6 +794,8 @@ kldfind(struct proc* p, struct kldfind_args* uap)
|
||||
linker_file_t lf;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
p->p_retval[0] = -1;
|
||||
|
||||
pathname = malloc(MAXPATHLEN, M_TEMP, M_WAITOK);
|
||||
@ -796,21 +813,27 @@ kldfind(struct proc* p, struct kldfind_args* uap)
|
||||
out:
|
||||
if (pathname)
|
||||
free(pathname, M_TEMP);
|
||||
return error;
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
kldnext(struct proc* p, struct kldnext_args* uap)
|
||||
{
|
||||
linker_file_t lf;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if (SCARG(uap, fileid) == 0) {
|
||||
if (TAILQ_FIRST(&linker_files))
|
||||
p->p_retval[0] = TAILQ_FIRST(&linker_files)->id;
|
||||
else
|
||||
p->p_retval[0] = 0;
|
||||
return 0;
|
||||
goto out;
|
||||
}
|
||||
|
||||
lf = linker_find_file_by_id(SCARG(uap, fileid));
|
||||
@ -819,12 +842,17 @@ kldnext(struct proc* p, struct kldnext_args* uap)
|
||||
p->p_retval[0] = TAILQ_NEXT(lf, link)->id;
|
||||
else
|
||||
p->p_retval[0] = 0;
|
||||
} else
|
||||
} else {
|
||||
error = ENOENT;
|
||||
|
||||
return error;
|
||||
}
|
||||
out:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
kldstat(struct proc* p, struct kldstat_args* uap)
|
||||
{
|
||||
@ -834,6 +862,8 @@ kldstat(struct proc* p, struct kldstat_args* uap)
|
||||
struct kld_file_stat* stat;
|
||||
int namelen;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
lf = linker_find_file_by_id(SCARG(uap, fileid));
|
||||
if (!lf) {
|
||||
error = ENOENT;
|
||||
@ -869,27 +899,36 @@ kldstat(struct proc* p, struct kldstat_args* uap)
|
||||
p->p_retval[0] = 0;
|
||||
|
||||
out:
|
||||
return error;
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
kldfirstmod(struct proc* p, struct kldfirstmod_args* uap)
|
||||
{
|
||||
linker_file_t lf;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
lf = linker_find_file_by_id(SCARG(uap, fileid));
|
||||
if (lf) {
|
||||
if (TAILQ_FIRST(&lf->modules))
|
||||
p->p_retval[0] = module_getid(TAILQ_FIRST(&lf->modules));
|
||||
else
|
||||
p->p_retval[0] = 0;
|
||||
} else
|
||||
} else {
|
||||
error = ENOENT;
|
||||
|
||||
return error;
|
||||
}
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
kldsym(struct proc *p, struct kldsym_args *uap)
|
||||
{
|
||||
@ -900,6 +939,8 @@ kldsym(struct proc *p, struct kldsym_args *uap)
|
||||
struct kld_sym_lookup lookup;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if ((error = copyin(SCARG(uap, data), &lookup, sizeof(lookup))) != 0)
|
||||
goto out;
|
||||
if (lookup.version != sizeof(lookup) || SCARG(uap, cmd) != KLDSYM_LOOKUP) {
|
||||
@ -940,7 +981,8 @@ kldsym(struct proc *p, struct kldsym_args *uap)
|
||||
out:
|
||||
if (symstr)
|
||||
free(symstr, M_TEMP);
|
||||
return error;
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -36,6 +36,8 @@
|
||||
#include <sys/module.h>
|
||||
#include <sys/linker.h>
|
||||
#include <sys/proc.h>
|
||||
#include <sys/lock.h>
|
||||
#include <sys/mutex.h>
|
||||
|
||||
static MALLOC_DEFINE(M_MODULE, "module", "module data structures");
|
||||
|
||||
@ -216,48 +218,67 @@ module_setspecific(module_t mod, modspecific_t *datap)
|
||||
/*
|
||||
* Syscalls.
|
||||
*/
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
modnext(struct proc* p, struct modnext_args* uap)
|
||||
{
|
||||
module_t mod;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
p->p_retval[0] = -1;
|
||||
if (SCARG(uap, modid) == 0) {
|
||||
mod = TAILQ_FIRST(&modules);
|
||||
if (mod) {
|
||||
if (mod)
|
||||
p->p_retval[0] = mod->id;
|
||||
return 0;
|
||||
} else
|
||||
return ENOENT;
|
||||
else
|
||||
error = ENOENT;
|
||||
goto done2;
|
||||
}
|
||||
|
||||
mod = module_lookupbyid(SCARG(uap, modid));
|
||||
if (!mod)
|
||||
return ENOENT;
|
||||
if (mod == NULL) {
|
||||
error = ENOENT;
|
||||
goto done2;
|
||||
}
|
||||
|
||||
if (TAILQ_NEXT(mod, link))
|
||||
p->p_retval[0] = TAILQ_NEXT(mod, link)->id;
|
||||
else
|
||||
p->p_retval[0] = 0;
|
||||
return 0;
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
modfnext(struct proc* p, struct modfnext_args* uap)
|
||||
{
|
||||
module_t mod;
|
||||
int error;
|
||||
|
||||
p->p_retval[0] = -1;
|
||||
|
||||
mod = module_lookupbyid(SCARG(uap, modid));
|
||||
if (!mod)
|
||||
return ENOENT;
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if (TAILQ_NEXT(mod, flink))
|
||||
p->p_retval[0] = TAILQ_NEXT(mod, flink)->id;
|
||||
else
|
||||
p->p_retval[0] = 0;
|
||||
return 0;
|
||||
mod = module_lookupbyid(SCARG(uap, modid));
|
||||
if (mod == NULL) {
|
||||
error = ENOENT;
|
||||
} else {
|
||||
error = 0;
|
||||
if (TAILQ_NEXT(mod, flink))
|
||||
p->p_retval[0] = TAILQ_NEXT(mod, flink)->id;
|
||||
else
|
||||
p->p_retval[0] = 0;
|
||||
}
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
struct module_stat_v1 {
|
||||
@ -267,6 +288,9 @@ struct module_stat_v1 {
|
||||
int id;
|
||||
};
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
modstat(struct proc* p, struct modstat_args* uap)
|
||||
{
|
||||
@ -276,9 +300,13 @@ modstat(struct proc* p, struct modstat_args* uap)
|
||||
int version;
|
||||
struct module_stat* stat;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
mod = module_lookupbyid(SCARG(uap, modid));
|
||||
if (!mod)
|
||||
return ENOENT;
|
||||
if (mod == NULL) {
|
||||
error = ENOENT;
|
||||
goto out;
|
||||
}
|
||||
|
||||
stat = SCARG(uap, stat);
|
||||
|
||||
@ -315,9 +343,13 @@ modstat(struct proc* p, struct modstat_args* uap)
|
||||
p->p_retval[0] = 0;
|
||||
|
||||
out:
|
||||
mtx_unlock(&Giant);
|
||||
return error;
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
modfind(struct proc* p, struct modfind_args* uap)
|
||||
{
|
||||
@ -328,12 +360,13 @@ modfind(struct proc* p, struct modfind_args* uap)
|
||||
if ((error = copyinstr(SCARG(uap, name), name, sizeof name, 0)) != 0)
|
||||
goto out;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
mod = module_lookupbyname(name);
|
||||
if (!mod)
|
||||
if (mod == NULL)
|
||||
error = ENOENT;
|
||||
else
|
||||
p->p_retval[0] = mod->id;
|
||||
|
||||
mtx_unlock(&Giant);
|
||||
out:
|
||||
return error;
|
||||
}
|
||||
|
@ -73,9 +73,12 @@ struct getpid_args {
|
||||
#endif
|
||||
|
||||
/*
|
||||
* getpid - MP SAFE
|
||||
* getpid
|
||||
*/
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getpid(p, uap)
|
||||
@ -83,17 +86,19 @@ getpid(p, uap)
|
||||
struct getpid_args *uap;
|
||||
{
|
||||
|
||||
mtx_lock(&Giant);
|
||||
p->p_retval[0] = p->p_pid;
|
||||
#if defined(COMPAT_43) || defined(COMPAT_SUNOS)
|
||||
PROC_LOCK(p);
|
||||
p->p_retval[1] = p->p_pptr->p_pid;
|
||||
PROC_UNLOCK(p);
|
||||
#endif
|
||||
mtx_unlock(&Giant);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* getppid - MP SAFE
|
||||
* getppid
|
||||
*/
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -101,6 +106,9 @@ struct getppid_args {
|
||||
int dummy;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getppid(p, uap)
|
||||
@ -108,9 +116,11 @@ getppid(p, uap)
|
||||
struct getppid_args *uap;
|
||||
{
|
||||
|
||||
mtx_lock(&Giant);
|
||||
PROC_LOCK(p);
|
||||
p->p_retval[0] = p->p_pptr->p_pid;
|
||||
PROC_UNLOCK(p);
|
||||
mtx_unlock(&Giant);
|
||||
return (0);
|
||||
}
|
||||
|
||||
@ -124,14 +134,18 @@ struct getpgrp_args {
|
||||
int dummy;
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
getpgrp(p, uap)
|
||||
struct proc *p;
|
||||
struct getpgrp_args *uap;
|
||||
{
|
||||
|
||||
mtx_lock(&Giant);
|
||||
p->p_retval[0] = p->p_pgrp->pg_id;
|
||||
mtx_unlock(&Giant);
|
||||
return (0);
|
||||
}
|
||||
|
||||
@ -142,27 +156,35 @@ struct getpgid_args {
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
getpgid(p, uap)
|
||||
struct proc *p;
|
||||
struct getpgid_args *uap;
|
||||
{
|
||||
struct proc *pt;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
if (uap->pid == 0)
|
||||
p->p_retval[0] = p->p_pgrp->pg_id;
|
||||
else {
|
||||
if ((pt = pfind(uap->pid)) == NULL)
|
||||
return ESRCH;
|
||||
if ((pt = pfind(uap->pid)) == NULL) {
|
||||
error = ESRCH;
|
||||
goto done2;
|
||||
}
|
||||
if ((error = p_cansee(p, pt))) {
|
||||
PROC_UNLOCK(pt);
|
||||
return (error);
|
||||
goto done2;
|
||||
}
|
||||
p->p_retval[0] = pt->p_pgrp->pg_id;
|
||||
PROC_UNLOCK(pt);
|
||||
}
|
||||
return 0;
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -174,27 +196,35 @@ struct getsid_args {
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
getsid(p, uap)
|
||||
struct proc *p;
|
||||
struct getsid_args *uap;
|
||||
{
|
||||
struct proc *pt;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
if (uap->pid == 0)
|
||||
mtx_lock(&Giant);
|
||||
if (uap->pid == 0) {
|
||||
p->p_retval[0] = p->p_session->s_sid;
|
||||
else {
|
||||
if ((pt = pfind(uap->pid)) == NULL)
|
||||
return ESRCH;
|
||||
} else {
|
||||
if ((pt = pfind(uap->pid)) == NULL) {
|
||||
error = ESRCH;
|
||||
goto done2;
|
||||
}
|
||||
if ((error = p_cansee(p, pt))) {
|
||||
PROC_UNLOCK(pt);
|
||||
return (error);
|
||||
goto done2;
|
||||
}
|
||||
p->p_retval[0] = pt->p_session->s_sid;
|
||||
PROC_UNLOCK(pt);
|
||||
}
|
||||
return 0;
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
|
||||
@ -207,6 +237,9 @@ struct getuid_args {
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getuid(p, uap)
|
||||
@ -214,10 +247,12 @@ getuid(p, uap)
|
||||
struct getuid_args *uap;
|
||||
{
|
||||
|
||||
mtx_lock(&Giant);
|
||||
p->p_retval[0] = p->p_ucred->cr_ruid;
|
||||
#if defined(COMPAT_43) || defined(COMPAT_SUNOS)
|
||||
p->p_retval[1] = p->p_ucred->cr_uid;
|
||||
#endif
|
||||
mtx_unlock(&Giant);
|
||||
return (0);
|
||||
}
|
||||
|
||||
@ -237,7 +272,9 @@ geteuid(p, uap)
|
||||
struct geteuid_args *uap;
|
||||
{
|
||||
|
||||
mtx_lock(&Giant);
|
||||
p->p_retval[0] = p->p_ucred->cr_uid;
|
||||
mtx_unlock(&Giant);
|
||||
return (0);
|
||||
}
|
||||
|
||||
@ -250,6 +287,9 @@ struct getgid_args {
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getgid(p, uap)
|
||||
@ -257,10 +297,12 @@ getgid(p, uap)
|
||||
struct getgid_args *uap;
|
||||
{
|
||||
|
||||
mtx_lock(&Giant);
|
||||
p->p_retval[0] = p->p_ucred->cr_rgid;
|
||||
#if defined(COMPAT_43) || defined(COMPAT_SUNOS)
|
||||
p->p_retval[1] = p->p_ucred->cr_groups[0];
|
||||
#endif
|
||||
mtx_unlock(&Giant);
|
||||
return (0);
|
||||
}
|
||||
|
||||
@ -275,6 +317,9 @@ struct getegid_args {
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getegid(p, uap)
|
||||
@ -282,7 +327,9 @@ getegid(p, uap)
|
||||
struct getegid_args *uap;
|
||||
{
|
||||
|
||||
mtx_lock(&Giant);
|
||||
p->p_retval[0] = p->p_ucred->cr_groups[0];
|
||||
mtx_unlock(&Giant);
|
||||
return (0);
|
||||
}
|
||||
|
||||
@ -292,27 +339,38 @@ struct getgroups_args {
|
||||
gid_t *gidset;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
getgroups(p, uap)
|
||||
struct proc *p;
|
||||
register struct getgroups_args *uap;
|
||||
{
|
||||
struct ucred *cred = p->p_ucred;
|
||||
struct ucred *cred;
|
||||
u_int ngrp;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
cred = p->p_ucred;
|
||||
if ((ngrp = uap->gidsetsize) == 0) {
|
||||
p->p_retval[0] = cred->cr_ngroups;
|
||||
return (0);
|
||||
error = 0;
|
||||
goto done2;
|
||||
}
|
||||
if (ngrp < cred->cr_ngroups) {
|
||||
error = EINVAL;
|
||||
goto done2;
|
||||
}
|
||||
if (ngrp < cred->cr_ngroups)
|
||||
return (EINVAL);
|
||||
ngrp = cred->cr_ngroups;
|
||||
if ((error = copyout((caddr_t)cred->cr_groups,
|
||||
(caddr_t)uap->gidset, ngrp * sizeof(gid_t))))
|
||||
return (error);
|
||||
(caddr_t)uap->gidset, ngrp * sizeof(gid_t)))) {
|
||||
goto done2;
|
||||
}
|
||||
p->p_retval[0] = ngrp;
|
||||
return (0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -321,20 +379,27 @@ struct setsid_args {
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setsid(p, uap)
|
||||
register struct proc *p;
|
||||
struct setsid_args *uap;
|
||||
{
|
||||
int error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
if (p->p_pgid == p->p_pid || pgfind(p->p_pid)) {
|
||||
return (EPERM);
|
||||
error = EPERM;
|
||||
} else {
|
||||
(void)enterpgrp(p, p->p_pid, 1);
|
||||
p->p_retval[0] = p->p_pid;
|
||||
return (0);
|
||||
error = 0;
|
||||
}
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -356,6 +421,9 @@ struct setpgid_args {
|
||||
int pgid; /* target pgrp id */
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setpgid(curp, uap)
|
||||
@ -368,24 +436,30 @@ setpgid(curp, uap)
|
||||
|
||||
if (uap->pgid < 0)
|
||||
return (EINVAL);
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if (uap->pid != 0 && uap->pid != curp->p_pid) {
|
||||
if ((targp = pfind(uap->pid)) == NULL || !inferior(targp)) {
|
||||
if (targp)
|
||||
PROC_UNLOCK(targp);
|
||||
return (ESRCH);
|
||||
error = ESRCH;
|
||||
goto done2;
|
||||
}
|
||||
if ((error = p_cansee(curproc, targp))) {
|
||||
PROC_UNLOCK(targp);
|
||||
return (error);
|
||||
goto done2;
|
||||
}
|
||||
if (targp->p_pgrp == NULL ||
|
||||
targp->p_session != curp->p_session) {
|
||||
PROC_UNLOCK(targp);
|
||||
return (EPERM);
|
||||
error = EPERM;
|
||||
goto done2;
|
||||
}
|
||||
if (targp->p_flag & P_EXEC) {
|
||||
PROC_UNLOCK(targp);
|
||||
return (EACCES);
|
||||
error = EACCES;
|
||||
goto done2;
|
||||
}
|
||||
} else {
|
||||
targp = curp;
|
||||
@ -393,19 +467,25 @@ setpgid(curp, uap)
|
||||
}
|
||||
if (SESS_LEADER(targp)) {
|
||||
PROC_UNLOCK(targp);
|
||||
return (EPERM);
|
||||
error = EPERM;
|
||||
goto done2;
|
||||
}
|
||||
if (uap->pgid == 0)
|
||||
if (uap->pgid == 0) {
|
||||
uap->pgid = targp->p_pid;
|
||||
else if (uap->pgid != targp->p_pid)
|
||||
} else if (uap->pgid != targp->p_pid) {
|
||||
if ((pgrp = pgfind(uap->pgid)) == 0 ||
|
||||
pgrp->pg_session != curp->p_session) {
|
||||
PROC_UNLOCK(targp);
|
||||
return (EPERM);
|
||||
error = EPERM;
|
||||
goto done2;
|
||||
}
|
||||
}
|
||||
/* XXX: We should probably hold the lock across enterpgrp. */
|
||||
PROC_UNLOCK(targp);
|
||||
return (enterpgrp(targp, uap->pgid, 0));
|
||||
error = enterpgrp(targp, uap->pgid, 0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -425,6 +505,9 @@ struct setuid_args {
|
||||
uid_t uid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setuid(p, uap)
|
||||
@ -433,10 +516,12 @@ setuid(p, uap)
|
||||
{
|
||||
struct ucred *newcred, *oldcred;
|
||||
uid_t uid;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
uid = uap->uid;
|
||||
oldcred = p->p_ucred;
|
||||
mtx_lock(&Giant);
|
||||
|
||||
/*
|
||||
* See if we have "permission" by POSIX 1003.1 rules.
|
||||
*
|
||||
@ -462,7 +547,7 @@ setuid(p, uap)
|
||||
uid != oldcred->cr_uid && /* allow setuid(geteuid()) */
|
||||
#endif
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)))
|
||||
return (error);
|
||||
goto done2;
|
||||
|
||||
newcred = crdup(oldcred);
|
||||
#ifdef _POSIX_SAVED_IDS
|
||||
@ -507,7 +592,9 @@ setuid(p, uap)
|
||||
}
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -515,6 +602,9 @@ struct seteuid_args {
|
||||
uid_t euid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
seteuid(p, uap)
|
||||
@ -523,14 +613,17 @@ seteuid(p, uap)
|
||||
{
|
||||
struct ucred *newcred, *oldcred;
|
||||
uid_t euid;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
euid = uap->euid;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
oldcred = p->p_ucred;
|
||||
if (euid != oldcred->cr_ruid && /* allow seteuid(getuid()) */
|
||||
euid != oldcred->cr_svuid && /* allow seteuid(saved uid) */
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)))
|
||||
return (error);
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT))) {
|
||||
goto done2;
|
||||
}
|
||||
/*
|
||||
* Everything's okay, do it. Copy credentials so other references do
|
||||
* not see our changes.
|
||||
@ -542,7 +635,9 @@ seteuid(p, uap)
|
||||
}
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -550,6 +645,9 @@ struct setgid_args {
|
||||
gid_t gid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setgid(p, uap)
|
||||
@ -558,9 +656,11 @@ setgid(p, uap)
|
||||
{
|
||||
struct ucred *newcred, *oldcred;
|
||||
gid_t gid;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
gid = uap->gid;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
oldcred = p->p_ucred;
|
||||
/*
|
||||
* See if we have "permission" by POSIX 1003.1 rules.
|
||||
@ -580,8 +680,9 @@ setgid(p, uap)
|
||||
#ifdef POSIX_APPENDIX_B_4_2_2 /* Use BSD-compat clause from B.4.2.2 */
|
||||
gid != oldcred->cr_groups[0] && /* allow setgid(getegid()) */
|
||||
#endif
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)))
|
||||
return (error);
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT))) {
|
||||
goto done2;
|
||||
}
|
||||
|
||||
newcred = crdup(oldcred);
|
||||
#ifdef _POSIX_SAVED_IDS
|
||||
@ -625,7 +726,9 @@ setgid(p, uap)
|
||||
}
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -633,6 +736,9 @@ struct setegid_args {
|
||||
gid_t egid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setegid(p, uap)
|
||||
@ -641,14 +747,17 @@ setegid(p, uap)
|
||||
{
|
||||
struct ucred *newcred, *oldcred;
|
||||
gid_t egid;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
egid = uap->egid;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
oldcred = p->p_ucred;
|
||||
if (egid != oldcred->cr_rgid && /* allow setegid(getgid()) */
|
||||
egid != oldcred->cr_svgid && /* allow setegid(saved gid) */
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)))
|
||||
return (error);
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT))) {
|
||||
goto done2;
|
||||
}
|
||||
newcred = crdup(oldcred);
|
||||
if (oldcred->cr_groups[0] != egid) {
|
||||
change_egid(newcred, egid);
|
||||
@ -656,7 +765,9 @@ setegid(p, uap)
|
||||
}
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -665,6 +776,9 @@ struct setgroups_args {
|
||||
gid_t *gidset;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setgroups(p, uap)
|
||||
@ -675,12 +789,16 @@ setgroups(p, uap)
|
||||
u_int ngrp;
|
||||
int error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
ngrp = uap->gidsetsize;
|
||||
oldcred = p->p_ucred;
|
||||
if ((error = suser_xxx(oldcred, NULL, PRISON_ROOT)))
|
||||
return (error);
|
||||
if (ngrp > NGROUPS)
|
||||
return (EINVAL);
|
||||
goto done2;
|
||||
if (ngrp > NGROUPS) {
|
||||
error = EINVAL;
|
||||
goto done2;
|
||||
}
|
||||
/*
|
||||
* XXX A little bit lazy here. We could test if anything has
|
||||
* changed before crcopy() and setting P_SUGID.
|
||||
@ -698,14 +816,16 @@ setgroups(p, uap)
|
||||
if ((error = copyin((caddr_t)uap->gidset,
|
||||
(caddr_t)newcred->cr_groups, ngrp * sizeof(gid_t)))) {
|
||||
crfree(newcred);
|
||||
return (error);
|
||||
goto done2;
|
||||
}
|
||||
newcred->cr_ngroups = ngrp;
|
||||
}
|
||||
setsugid(p);
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -714,6 +834,9 @@ struct setreuid_args {
|
||||
uid_t euid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setreuid(p, uap)
|
||||
@ -722,17 +845,21 @@ setreuid(p, uap)
|
||||
{
|
||||
struct ucred *newcred, *oldcred;
|
||||
uid_t ruid, euid;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
ruid = uap->ruid;
|
||||
euid = uap->euid;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
oldcred = p->p_ucred;
|
||||
if (((ruid != (uid_t)-1 && ruid != oldcred->cr_ruid &&
|
||||
ruid != oldcred->cr_svuid) ||
|
||||
(euid != (uid_t)-1 && euid != oldcred->cr_uid &&
|
||||
euid != oldcred->cr_ruid && euid != oldcred->cr_svuid)) &&
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)) != 0)
|
||||
return (error);
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)) != 0) {
|
||||
goto done2;
|
||||
}
|
||||
newcred = crdup(oldcred);
|
||||
if (euid != (uid_t)-1 && oldcred->cr_uid != euid) {
|
||||
change_euid(newcred, euid);
|
||||
@ -749,7 +876,9 @@ setreuid(p, uap)
|
||||
}
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -758,6 +887,9 @@ struct setregid_args {
|
||||
gid_t egid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setregid(p, uap)
|
||||
@ -766,17 +898,21 @@ setregid(p, uap)
|
||||
{
|
||||
struct ucred *newcred, *oldcred;
|
||||
gid_t rgid, egid;
|
||||
int error;
|
||||
int error = 0;
|
||||
|
||||
rgid = uap->rgid;
|
||||
egid = uap->egid;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
oldcred = p->p_ucred;
|
||||
if (((rgid != (gid_t)-1 && rgid != oldcred->cr_rgid &&
|
||||
rgid != oldcred->cr_svgid) ||
|
||||
(egid != (gid_t)-1 && egid != oldcred->cr_groups[0] &&
|
||||
egid != oldcred->cr_rgid && egid != oldcred->cr_svgid)) &&
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)) != 0)
|
||||
return (error);
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)) != 0) {
|
||||
goto done2;
|
||||
}
|
||||
|
||||
newcred = crdup(oldcred);
|
||||
if (egid != (gid_t)-1 && oldcred->cr_groups[0] != egid) {
|
||||
@ -794,7 +930,9 @@ setregid(p, uap)
|
||||
}
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -809,6 +947,9 @@ struct setresuid_args {
|
||||
uid_t suid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setresuid(p, uap)
|
||||
@ -822,6 +963,8 @@ setresuid(p, uap)
|
||||
ruid = uap->ruid;
|
||||
euid = uap->euid;
|
||||
suid = uap->suid;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
oldcred = p->p_ucred;
|
||||
if (((ruid != (uid_t)-1 && ruid != oldcred->cr_ruid &&
|
||||
ruid != oldcred->cr_svuid &&
|
||||
@ -832,8 +975,9 @@ setresuid(p, uap)
|
||||
(suid != (uid_t)-1 && suid != oldcred->cr_ruid &&
|
||||
suid != oldcred->cr_svuid &&
|
||||
suid != oldcred->cr_uid)) &&
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)) != 0)
|
||||
return (error);
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)) != 0) {
|
||||
goto done2;
|
||||
}
|
||||
|
||||
newcred = crdup(oldcred);
|
||||
if (euid != (uid_t)-1 && oldcred->cr_uid != euid) {
|
||||
@ -850,7 +994,10 @@ setresuid(p, uap)
|
||||
}
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
error = 0;
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -865,6 +1012,9 @@ struct setresgid_args {
|
||||
gid_t sgid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setresgid(p, uap)
|
||||
@ -878,6 +1028,8 @@ setresgid(p, uap)
|
||||
rgid = uap->rgid;
|
||||
egid = uap->egid;
|
||||
sgid = uap->sgid;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
oldcred = p->p_ucred;
|
||||
if (((rgid != (gid_t)-1 && rgid != oldcred->cr_rgid &&
|
||||
rgid != oldcred->cr_svgid &&
|
||||
@ -888,9 +1040,9 @@ setresgid(p, uap)
|
||||
(sgid != (gid_t)-1 && sgid != oldcred->cr_rgid &&
|
||||
sgid != oldcred->cr_svgid &&
|
||||
sgid != oldcred->cr_groups[0])) &&
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)) != 0)
|
||||
return (error);
|
||||
|
||||
(error = suser_xxx(oldcred, NULL, PRISON_ROOT)) != 0) {
|
||||
goto done2;
|
||||
}
|
||||
newcred = crdup(oldcred);
|
||||
if (egid != (gid_t)-1 && oldcred->cr_groups[0] != egid) {
|
||||
change_egid(newcred, egid);
|
||||
@ -906,7 +1058,10 @@ setresgid(p, uap)
|
||||
}
|
||||
p->p_ucred = newcred;
|
||||
crfree(oldcred);
|
||||
return (0);
|
||||
error = 0;
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -916,15 +1071,21 @@ struct getresuid_args {
|
||||
uid_t *suid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getresuid(p, uap)
|
||||
register struct proc *p;
|
||||
struct getresuid_args *uap;
|
||||
{
|
||||
struct ucred *cred = p->p_ucred;
|
||||
struct ucred *cred;
|
||||
int error1 = 0, error2 = 0, error3 = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
cred = p->p_ucred;
|
||||
|
||||
if (uap->ruid)
|
||||
error1 = copyout((caddr_t)&cred->cr_ruid,
|
||||
(caddr_t)uap->ruid, sizeof(cred->cr_ruid));
|
||||
@ -934,6 +1095,7 @@ getresuid(p, uap)
|
||||
if (uap->suid)
|
||||
error3 = copyout((caddr_t)&cred->cr_svuid,
|
||||
(caddr_t)uap->suid, sizeof(cred->cr_svuid));
|
||||
mtx_unlock(&Giant);
|
||||
return error1 ? error1 : (error2 ? error2 : error3);
|
||||
}
|
||||
|
||||
@ -944,15 +1106,21 @@ struct getresgid_args {
|
||||
gid_t *sgid;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getresgid(p, uap)
|
||||
register struct proc *p;
|
||||
struct getresgid_args *uap;
|
||||
{
|
||||
struct ucred *cred = p->p_ucred;
|
||||
struct ucred *cred;
|
||||
int error1 = 0, error2 = 0, error3 = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
cred = p->p_ucred;
|
||||
|
||||
if (uap->rgid)
|
||||
error1 = copyout((caddr_t)&cred->cr_rgid,
|
||||
(caddr_t)uap->rgid, sizeof(cred->cr_rgid));
|
||||
@ -962,6 +1130,7 @@ getresgid(p, uap)
|
||||
if (uap->sgid)
|
||||
error3 = copyout((caddr_t)&cred->cr_svgid,
|
||||
(caddr_t)uap->sgid, sizeof(cred->cr_svgid));
|
||||
mtx_unlock(&Giant);
|
||||
return error1 ? error1 : (error2 ? error2 : error3);
|
||||
}
|
||||
|
||||
@ -989,23 +1158,31 @@ issetugid(p, uap)
|
||||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
__setugid(p, uap)
|
||||
struct proc *p;
|
||||
struct __setugid_args *uap;
|
||||
{
|
||||
|
||||
#ifdef REGRESSION
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
switch (uap->flag) {
|
||||
case 0:
|
||||
p->p_flag &= ~P_SUGID;
|
||||
return (0);
|
||||
break;
|
||||
case 1:
|
||||
p->p_flag |= P_SUGID;
|
||||
return (0);
|
||||
break;
|
||||
default:
|
||||
return (EINVAL);
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
#else /* !REGRESSION */
|
||||
return (ENOSYS);
|
||||
#endif /* !REGRESSION */
|
||||
@ -1384,17 +1561,24 @@ struct getlogin_args {
|
||||
u_int namelen;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getlogin(p, uap)
|
||||
struct proc *p;
|
||||
struct getlogin_args *uap;
|
||||
{
|
||||
int error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
if (uap->namelen > MAXLOGNAME)
|
||||
uap->namelen = MAXLOGNAME;
|
||||
return (copyout((caddr_t) p->p_pgrp->pg_session->s_login,
|
||||
(caddr_t) uap->namebuf, uap->namelen));
|
||||
error = copyout((caddr_t) p->p_pgrp->pg_session->s_login,
|
||||
(caddr_t) uap->namebuf, uap->namelen);
|
||||
mtx_unlock(&Giant);
|
||||
return(error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1405,6 +1589,9 @@ struct setlogin_args {
|
||||
char *namebuf;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setlogin(p, uap)
|
||||
@ -1414,15 +1601,19 @@ setlogin(p, uap)
|
||||
int error;
|
||||
char logintmp[MAXLOGNAME];
|
||||
|
||||
mtx_lock(&Giant);
|
||||
if ((error = suser_xxx(0, p, PRISON_ROOT)))
|
||||
return (error);
|
||||
goto done2;
|
||||
error = copyinstr((caddr_t) uap->namebuf, (caddr_t) logintmp,
|
||||
sizeof(logintmp), (size_t *)0);
|
||||
if (error == ENAMETOOLONG)
|
||||
if (error == ENAMETOOLONG) {
|
||||
error = EINVAL;
|
||||
else if (!error)
|
||||
} else if (!error) {
|
||||
(void) memcpy(p->p_pgrp->pg_session->s_login, logintmp,
|
||||
sizeof(logintmp));
|
||||
}
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
|
@ -80,6 +80,9 @@ struct getpriority_args {
|
||||
int who;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
int
|
||||
getpriority(curp, uap)
|
||||
struct proc *curp;
|
||||
@ -87,9 +90,11 @@ getpriority(curp, uap)
|
||||
{
|
||||
register struct proc *p;
|
||||
register int low = PRIO_MAX + 1;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
switch (uap->which) {
|
||||
|
||||
case PRIO_PROCESS:
|
||||
if (uap->who == 0)
|
||||
low = curp->p_nice;
|
||||
@ -130,12 +135,14 @@ getpriority(curp, uap)
|
||||
break;
|
||||
|
||||
default:
|
||||
return (EINVAL);
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
if (low == PRIO_MAX + 1)
|
||||
return (ESRCH);
|
||||
if (low == PRIO_MAX + 1 && error == 0)
|
||||
error = ESRCH;
|
||||
curp->p_retval[0] = low;
|
||||
return (0);
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -145,6 +152,9 @@ struct setpriority_args {
|
||||
int prio;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setpriority(curp, uap)
|
||||
@ -154,8 +164,9 @@ setpriority(curp, uap)
|
||||
register struct proc *p;
|
||||
int found = 0, error = 0;
|
||||
|
||||
switch (uap->which) {
|
||||
mtx_lock(&Giant);
|
||||
|
||||
switch (uap->which) {
|
||||
case PRIO_PROCESS:
|
||||
if (uap->who == 0)
|
||||
error = donice(curp, curp, uap->prio);
|
||||
@ -200,10 +211,12 @@ setpriority(curp, uap)
|
||||
break;
|
||||
|
||||
default:
|
||||
return (EINVAL);
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
if (found == 0)
|
||||
return (ESRCH);
|
||||
if (found == 0 && error == 0)
|
||||
error = ESRCH;
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
@ -240,6 +253,9 @@ struct rtprio_args {
|
||||
* Set realtime priority
|
||||
*/
|
||||
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
rtprio(curp, uap)
|
||||
@ -250,14 +266,19 @@ rtprio(curp, uap)
|
||||
struct rtprio rtp;
|
||||
int error;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
if (uap->pid == 0) {
|
||||
p = curp;
|
||||
PROC_LOCK(p);
|
||||
} else
|
||||
} else {
|
||||
p = pfind(uap->pid);
|
||||
}
|
||||
|
||||
if (p == NULL)
|
||||
return (ESRCH);
|
||||
if (p == NULL) {
|
||||
error = ESRCH;
|
||||
goto done2;
|
||||
}
|
||||
|
||||
switch (uap->function) {
|
||||
case RTP_LOOKUP:
|
||||
@ -300,6 +321,8 @@ rtprio(curp, uap)
|
||||
break;
|
||||
}
|
||||
PROC_UNLOCK(p);
|
||||
done2:
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
@ -355,6 +378,9 @@ struct osetrlimit_args {
|
||||
struct orlimit *rlp;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
osetrlimit(p, uap)
|
||||
@ -370,7 +396,10 @@ osetrlimit(p, uap)
|
||||
return (error);
|
||||
lim.rlim_cur = olim.rlim_cur;
|
||||
lim.rlim_max = olim.rlim_max;
|
||||
return (dosetrlimit(p, uap->which, &lim));
|
||||
mtx_lock(&Giant);
|
||||
error = dosetrlimit(p, uap->which, &lim);
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef _SYS_SYSPROTO_H_
|
||||
@ -379,6 +408,9 @@ struct ogetrlimit_args {
|
||||
struct orlimit *rlp;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
ogetrlimit(p, uap)
|
||||
@ -386,16 +418,20 @@ ogetrlimit(p, uap)
|
||||
register struct ogetrlimit_args *uap;
|
||||
{
|
||||
struct orlimit olim;
|
||||
int error;
|
||||
|
||||
if (uap->which >= RLIM_NLIMITS)
|
||||
return (EINVAL);
|
||||
mtx_lock(&Giant);
|
||||
olim.rlim_cur = p->p_rlimit[uap->which].rlim_cur;
|
||||
if (olim.rlim_cur == -1)
|
||||
olim.rlim_cur = 0x7fffffff;
|
||||
olim.rlim_max = p->p_rlimit[uap->which].rlim_max;
|
||||
if (olim.rlim_max == -1)
|
||||
olim.rlim_max = 0x7fffffff;
|
||||
return (copyout((caddr_t)&olim, (caddr_t)uap->rlp, sizeof(olim)));
|
||||
error = copyout((caddr_t)&olim, (caddr_t)uap->rlp, sizeof(olim));
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
#endif /* COMPAT_43 || COMPAT_SUNOS */
|
||||
|
||||
@ -405,6 +441,9 @@ struct __setrlimit_args {
|
||||
struct rlimit *rlp;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
setrlimit(p, uap)
|
||||
@ -417,7 +456,10 @@ setrlimit(p, uap)
|
||||
if ((error =
|
||||
copyin((caddr_t)uap->rlp, (caddr_t)&alim, sizeof (struct rlimit))))
|
||||
return (error);
|
||||
return (dosetrlimit(p, uap->which, &alim));
|
||||
mtx_lock(&Giant);
|
||||
error = dosetrlimit(p, uap->which, &alim);
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
int
|
||||
@ -531,17 +573,24 @@ struct __getrlimit_args {
|
||||
struct rlimit *rlp;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getrlimit(p, uap)
|
||||
struct proc *p;
|
||||
register struct __getrlimit_args *uap;
|
||||
{
|
||||
int error;
|
||||
|
||||
if (uap->which >= RLIM_NLIMITS)
|
||||
return (EINVAL);
|
||||
return (copyout((caddr_t)&p->p_rlimit[uap->which], (caddr_t)uap->rlp,
|
||||
sizeof (struct rlimit)));
|
||||
mtx_lock(&Giant);
|
||||
error = copyout((caddr_t)&p->p_rlimit[uap->which], (caddr_t)uap->rlp,
|
||||
sizeof (struct rlimit));
|
||||
mtx_unlock(&Giant);
|
||||
return(error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -645,6 +694,9 @@ struct getrusage_args {
|
||||
struct rusage *rusage;
|
||||
};
|
||||
#endif
|
||||
/*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
getrusage(p, uap)
|
||||
@ -652,9 +704,11 @@ getrusage(p, uap)
|
||||
register struct getrusage_args *uap;
|
||||
{
|
||||
register struct rusage *rup;
|
||||
int error = 0;
|
||||
|
||||
mtx_lock(&Giant);
|
||||
|
||||
switch (uap->who) {
|
||||
|
||||
case RUSAGE_SELF:
|
||||
rup = &p->p_stats->p_ru;
|
||||
mtx_lock_spin(&sched_lock);
|
||||
@ -667,10 +721,16 @@ getrusage(p, uap)
|
||||
break;
|
||||
|
||||
default:
|
||||
return (EINVAL);
|
||||
rup = NULL;
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
return (copyout((caddr_t)rup, (caddr_t)uap->rusage,
|
||||
sizeof (struct rusage)));
|
||||
mtx_unlock(&Giant);
|
||||
if (error == 0) {
|
||||
error = copyout((caddr_t)rup, (caddr_t)uap->rusage,
|
||||
sizeof (struct rusage));
|
||||
}
|
||||
return(error);
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -131,21 +131,23 @@ shutdown_conf(void *unused)
|
||||
|
||||
SYSINIT(shutdown_conf, SI_SUB_INTRINSIC, SI_ORDER_ANY, shutdown_conf, NULL)
|
||||
|
||||
/* ARGSUSED */
|
||||
|
||||
/*
|
||||
* The system call that results in a reboot
|
||||
*
|
||||
* MPSAFE
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
int
|
||||
reboot(struct proc *p, struct reboot_args *uap)
|
||||
{
|
||||
int error;
|
||||
|
||||
if ((error = suser(p)))
|
||||
return (error);
|
||||
|
||||
boot(uap->opt);
|
||||
return (0);
|
||||
mtx_lock(&Giant);
|
||||
if ((error = suser(p)) == 0) {
|
||||
boot(uap->opt);
|
||||
}
|
||||
mtx_unlock(&Giant);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -565,14 +567,27 @@ static u_int panic_cpu = NOCPU;
|
||||
* Panic is called on unresolvable fatal errors. It prints "panic: mesg",
|
||||
* and then reboots. If we are called twice, then we avoid trying to sync
|
||||
* the disks as this often leads to recursive panics.
|
||||
*
|
||||
* MPSAFE
|
||||
*/
|
||||
void
|
||||
panic(const char *fmt, ...)
|
||||
{
|
||||
int bootopt;
|
||||
int holding_giant = 0;
|
||||
va_list ap;
|
||||
static char buf[256];
|
||||
|
||||
#if 0
|
||||
/*
|
||||
* We must hold Giant when entering a panic
|
||||
*/
|
||||
if (!mtx_owned(&Giant)) {
|
||||
mtx_lock(&Giant);
|
||||
holding_giant = 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef SMP
|
||||
/*
|
||||
* We don't want multiple CPU's to panic at the same time, so we
|
||||
@ -580,11 +595,13 @@ panic(const char *fmt, ...)
|
||||
* panic_cpu if we are spinning in case the panic on the first
|
||||
* CPU is canceled.
|
||||
*/
|
||||
if (panic_cpu != PCPU_GET(cpuid))
|
||||
if (panic_cpu != PCPU_GET(cpuid)) {
|
||||
while (atomic_cmpset_int(&panic_cpu, NOCPU,
|
||||
PCPU_GET(cpuid)) == 0)
|
||||
PCPU_GET(cpuid)) == 0) {
|
||||
while (panic_cpu != NOCPU)
|
||||
; /* nothing */
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
bootopt = RB_AUTOBOOT | RB_DUMP;
|
||||
@ -616,6 +633,8 @@ panic(const char *fmt, ...)
|
||||
#ifdef SMP
|
||||
atomic_store_rel_int(&panic_cpu, NOCPU);
|
||||
#endif
|
||||
if (holding_giant)
|
||||
mtx_unlock(&Giant);
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
|
Loading…
Reference in New Issue
Block a user