lseek.o mlockall.o mmap.o msgctl.o msgget.o msgrcv.o msgsnd.o \
munlockall.o openbsd_poll.o semconfig.o semget.o \
semop.o setdomainname.o shmat.o shmctl.o shmdt.o shmget.o sstk.o \
- thr_sleep.o thr_wakeup.o truncate.o uname.o vfork.o yield.o
+ truncate.o uname.o vfork.o yield.o
PSEUDO= _getlogin.o _exit.o
* owait()
*
* owait_args(int dummy)
+ *
+ * MPSAFE
*/
int
sys_owait(struct owait_args *uap)
#include <vfs/union/union.h>
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ocreat(struct ocreat_args *uap)
{
struct nlookupdata nd;
int error;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_open(&nd, O_WRONLY | O_CREAT | O_TRUNC,
uap->mode, &uap->sysmsg_iresult);
}
+ rel_mplock();
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_oftruncate(struct oftruncate_args *uap)
{
int error;
+ get_mplock();
error = kern_ftruncate(uap->fd, uap->length);
+ rel_mplock();
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_olseek(struct olseek_args *uap)
{
int error;
error = kern_lseek(uap->fd, uap->offset, uap->whence,
- &uap->sysmsg_offset);
+ &uap->sysmsg_offset);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_otruncate(struct otruncate_args *uap)
{
struct nlookupdata nd;
int error;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0)
error = kern_truncate(&nd, uap->length);
nlookup_done(&nd);
+ rel_mplock();
return (error);
}
char od_name[];
};
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ogetdirentries(struct ogetdirentries_args *uap)
{
buf = kmalloc(len, M_TEMP, M_WAITOK);
+ get_mplock();
error = kern_getdirentries(uap->fd, buf, len,
- &base, &bytes_transfered, UIO_SYSSPACE);
+ &base, &bytes_transfered, UIO_SYSSPACE);
+ rel_mplock();
if (error) {
kfree(buf, M_TEMP);
#include <sys/sysctl.h>
#include <vm/vm_param.h>
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ogethostname(struct gethostname_args *uap)
{
len = MIN(uap->len, MAXHOSTNAMELEN);
hostname = kmalloc(MAXHOSTNAMELEN, M_TEMP, M_WAITOK);
+ get_mplock();
error = kernel_sysctl(name, 2, hostname, &len, NULL, 0, NULL);
+ rel_mplock();
if (error == 0)
error = copyout(hostname, uap->hostname, len);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_osethostname(struct sethostname_args *uap)
{
return (error);
}
+ get_mplock();
error = kernel_sysctl(name, 2, NULL, 0, hostname, len, NULL);
+ rel_mplock();
kfree(hostname, M_TEMP);
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_ogethostid(struct ogethostid_args *uap)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_osethostid(struct osethostid_args *uap)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_oquota(struct oquota_args *uap)
{
*/
static char bsdi_strings[80]; /* It had better be less than this! */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ogetkerninfo(struct getkerninfo_args *uap)
{
size_t size;
u_int needed = 0;
- switch (uap->op & 0xff00) {
+ get_mplock();
+ switch (uap->op & 0xff00) {
case KINFO_RT:
name[0] = CTL_NET;
name[1] = PF_ROUTE;
}
break;
}
-
default:
- return (EOPNOTSUPP);
+ error = EOPNOTSUPP;
+ break;
}
+ rel_mplock();
if (error)
return (error);
uap->sysmsg_iresult = (int)size;
if (uap->size)
- error = copyout((caddr_t)&size, (caddr_t)uap->size,
- sizeof(size));
+ error = copyout(&size, uap->size, sizeof(size));
return (error);
}
#include <sys/kern_syscall.h>
#include <sys/resourcevar.h>
+/*
+ * MPSAFE
+ */
int
sys_ogetrlimit(struct ogetrlimit_args *uap)
{
}
+/*
+ * MPSAFE
+ */
int
sys_osetrlimit(struct osetrlimit_args *uap)
{
* This file is provided for educational purposes only. The osigvec()
* syscall is probably broken because the current signal code uses
* a different signal trampoline.
+ *
+ * MPALMOSTSAFE
*/
-
int
sys_osigvec(struct osigvec_args *uap)
{
nsap->sa_flags ^= SA_RESTART; /* opposite of SV_INTERRUPT */
}
+ get_mplock();
error = kern_sigaction(uap->signum, nsap, osap);
+ rel_mplock();
if (osap && !error) {
vec.sv_handler = osap->sa_handler;
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_osigblock(struct osigblock_args *uap)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_osigsetmask(struct osigsetmask_args *uap)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_osigstack(struct osigstack_args *uap)
{
ss.ss_sp = lp->lwp_sigstk.ss_sp;
ss.ss_onstack = lp->lwp_sigstk.ss_flags & SS_ONSTACK;
if (uap->oss && (error = copyout(&ss, uap->oss,
- sizeof(struct sigstack))))
+ sizeof(struct sigstack)))) {
return (error);
+ }
if (uap->nss && (error = copyin(uap->nss, &ss, sizeof(ss))) == 0) {
lp->lwp_sigstk.ss_sp = ss.ss_sp;
lp->lwp_sigstk.ss_size = 0;
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_okillpg(struct okillpg_args *uap)
{
int error;
+ get_mplock();
error = kern_kill(uap->signum, -uap->pgid, -1);
+ rel_mplock();
return (error);
}
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_oaccept(struct accept_args *uap)
{
if (error)
return (error);
+ get_mplock();
error = kern_accept(uap->s, 0, &sa, &sa_len,
&uap->sysmsg_iresult);
+ rel_mplock();
if (error) {
/*
if (sa)
FREE(sa, M_SONAME);
} else {
+ get_mplock();
error = kern_accept(uap->s, 0, NULL, 0, &uap->sysmsg_iresult);
+ rel_mplock();
}
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ogetsockname(struct getsockname_args *uap)
{
if (error)
return (error);
+ get_mplock();
error = kern_getsockname(uap->fdes, &sa, &sa_len);
+ rel_mplock();
if (error == 0)
error = compat_43_copyout_sockaddr(sa, uap->asa, sa_len);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ogetpeername(struct ogetpeername_args *uap)
{
if (error)
return (error);
+ get_mplock();
error = kern_getpeername(uap->fdes, &sa, &sa_len);
+ rel_mplock();
if (error == 0) {
error = compat_43_copyout_sockaddr(sa, uap->asa, sa_len);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_osend(struct osend_args *uap)
{
auio.uio_rw = UIO_WRITE;
auio.uio_td = td;
+ get_mplock();
error = kern_sendmsg(uap->s, NULL, &auio, NULL, uap->flags,
&uap->sysmsg_szresult);
+ rel_mplock();
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_osendmsg(struct osendmsg_args *uap)
{
}
}
+ get_mplock();
error = kern_sendmsg(uap->s, sa, &auio, control, uap->flags,
&uap->sysmsg_szresult);
+ rel_mplock();
cleanup:
iovec_free(&iov, aiov);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_orecv(struct orecv_args *uap)
{
auio.uio_rw = UIO_READ;
auio.uio_td = td;
+ get_mplock();
error = kern_recvmsg(uap->s, NULL, &auio, NULL, &uap->flags,
&uap->sysmsg_szresult);
+ rel_mplock();
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_orecvfrom(struct recvfrom_args *uap)
{
auio.uio_rw = UIO_READ;
auio.uio_td = td;
+ get_mplock();
error = kern_recvmsg(uap->s, uap->from ? &sa : NULL, &auio, NULL,
&uap->flags, &uap->sysmsg_szresult);
+ rel_mplock();
if (error == 0 && uap->from) {
if (sa != NULL) {
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_orecvmsg(struct orecvmsg_args *uap)
{
flags = msg.msg_flags;
+ get_mplock();
error = kern_recvmsg(uap->s, (msg.msg_name ? &sa : NULL), &auio,
(msg.msg_control ? &control : NULL), &flags,
&uap->sysmsg_szresult);
+ rel_mplock();
/*
* Copyout msg.msg_name and msg.msg_namelen.
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ofstat(struct ofstat_args *uap)
{
struct stat st;
int error;
+ get_mplock();
error = kern_fstat(uap->fd, &st);
if (error == 0)
error = compat_43_copyout_stat(&st, uap->sb);
+ rel_mplock();
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ostat(struct ostat_args *uap)
{
struct stat st;
int error;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_stat(&nd, &st);
error = compat_43_copyout_stat(&st, uap->ub);
nlookup_done(&nd);
}
+ rel_mplock();
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_olstat(struct olstat_args *uap)
{
struct stat st;
int error;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, 0);
if (error == 0) {
error = kern_stat(&nd, &st);
error = compat_43_copyout_stat(&st, uap->ub);
nlookup_done(&nd);
}
+ rel_mplock();
return (error);
}
#include <sys/proc.h>
#include <sys/thread2.h>
+/*
+ * MPSAFE
+ */
int
sys_ovadvise(struct ovadvise_args *uap)
{
return (EINVAL);
}
+/*
+ * MPSAFE
+ */
int
sys_ogetpagesize(struct getpagesize_args *uap)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_ommap(struct ommap_args *uap)
{
if (uap->flags & OMAP_INHERIT)
flags |= MAP_INHERIT;
+ get_mplock();
error = kern_mmap(curproc->p_vmspace, uap->addr, uap->len,
prot, flags, uap->fd, uap->pos,
&uap->sysmsg_resultp);
+ rel_mplock();
return (error);
}
char df12_d_name[];
};
+/*
+ * MPALMOSTSAFE
+ */
static int
common_getdirentries(long *base, int *result, int fd, char *usr_buf, size_t count)
{
buf = kmalloc(len, M_TEMP, M_WAITOK);
- error = kern_getdirentries(fd, buf, len,
- base, &bytes_transfered, UIO_SYSSPACE);
+ get_mplock();
+ error = kern_getdirentries(fd, buf, len, base,
+ &bytes_transfered, UIO_SYSSPACE);
+ rel_mplock();
if (error) {
kfree(buf, M_TEMP);
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_dfbsd12_getdirentries(struct dfbsd12_getdirentries_args *uap)
{
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_dfbsd12_getdents(struct dfbsd12_getdents_args *uap)
{
* stat_args(char *path, struct dfbsd12_stat *ub)
*
* Get file status; this version follows links.
+ *
+ * MPALMOSTSAFE
*/
int
sys_dfbsd12_stat(struct dfbsd12_stat_args *uap)
struct stat st;
int error;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_stat(&nd, &st);
}
}
nlookup_done(&nd);
+ rel_mplock();
return (error);
}
* lstat_args(char *path, struct dfbsd12_stat *ub)
*
* Get file status; this version does not follow links.
+ *
+ * MPALMOSTSAFE
*/
int
sys_dfbsd12_lstat(struct dfbsd12_lstat_args *uap)
struct stat st;
int error;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, 0);
if (error == 0) {
error = kern_stat(&nd, &st);
}
}
nlookup_done(&nd);
+ rel_mplock();
return (error);
}
/*
* fhstat_args(struct fhandle *u_fhp, struct dfbsd12_stat *sb)
+ *
+ * MPALMOSTSAFE
*/
int
sys_dfbsd12_fhstat(struct dfbsd12_fhstat_args *uap)
if (error)
return (error);
- if ((mp = vfs_getvfs(&fh.fh_fsid)) == NULL)
- return (ESTALE);
+ get_mplock();
+ if ((mp = vfs_getvfs(&fh.fh_fsid)) == NULL) {
+ error = ESTALE;
+ goto done;
+ }
if ((error = VFS_FHTOVP(mp, NULL, &fh.fh_fid, &vp)))
- return (error);
+ goto done;
error = vn_stat(vp, &sb, td->td_proc->p_ucred);
vput(vp);
if (error)
- return (error);
+ goto done;
cvtstat(&osb, &sb);
error = copyout(&osb, uap->sb, sizeof(osb));
+done:
+ rel_mplock();
return (error);
}
/*
* dfbsd12_fstat_args(int fd, struct dfbsd12_stat *sb)
+ *
+ * MPALMOSTSAFE
*/
int
sys_dfbsd12_fstat(struct dfbsd12_fstat_args *uap)
struct stat st;
int error;
+ get_mplock();
error = kern_fstat(uap->fd, &st);
+ rel_mplock();
if (error == 0) {
cvtstat(&ost, &st);
return (lsa);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_execve(struct linux_execve_args *args)
{
if (ldebug(execve))
kprintf(ARGS(execve, "%s"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
bzero(&exec_args, sizeof(exec_args));
if (error == 0) {
exit1(W_EXITCODE(0, SIGABRT));
/* NOTREACHED */
}
+ rel_mplock();
return(error);
}
l_long msgtyp;
};
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_ipc(struct linux_ipc_args *args)
{
int error = 0;
+ get_mplock();
+
switch (args->what & 0xFFFF) {
case LINUX_SEMOP: {
struct linux_semop_args a;
a.sysmsg_lresult = 0;
error = copyin((caddr_t)args->ptr, &a.arg, sizeof(a.arg));
if (error)
- return (error);
+ break;
error = linux_semctl(&a);
args->sysmsg_lresult = a.sysmsg_lresult;
break;
struct l_ipc_kludge tmp;
int error;
- if (args->ptr == NULL)
- return (EINVAL);
+ if (args->ptr == NULL) {
+ error = EINVAL;
+ break;
+ }
error = copyin((caddr_t)args->ptr, &tmp, sizeof(tmp));
if (error)
- return (error);
+ break;
a.msgp = tmp.msgp;
a.msgtyp = tmp.msgtyp;
} else {
error = EINVAL;
break;
}
+ rel_mplock();
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_old_select(struct linux_old_select_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_fork(struct linux_fork_args *args)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_exit_group(struct linux_exit_group_args *args)
{
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_vfork(struct linux_vfork_args *args)
{
#define CLONE_SIGHAND 0x800
#define CLONE_PID 0x1000
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_clone(struct linux_clone_args *args)
{
rf_args.flags = ff;
rf_args.sysmsg_iresult = 0;
- if ((error = sys_rfork(&rf_args)) != 0)
- return (error);
- args->sysmsg_iresult = rf_args.sysmsg_iresult;
-
- p2 = pfind(rf_args.sysmsg_iresult);
- if (p2 == NULL)
- return (ESRCH);
+ get_mplock();
+ if ((error = sys_rfork(&rf_args)) == 0) {
+ args->sysmsg_iresult = rf_args.sysmsg_iresult;
- p2->p_sigparent = exit_signal;
- ONLY_LWP_IN_PROC(p2)->lwp_md.md_regs->tf_esp =
- (unsigned int)args->stack;
+ p2 = pfind(rf_args.sysmsg_iresult);
+ if (p2 == NULL)
+ error = ESRCH;
+ }
+ rel_mplock();
+ if (error == 0) {
+ p2->p_sigparent = exit_signal;
+ ONLY_LWP_IN_PROC(p2)->lwp_md.md_regs->tf_esp =
+ (unsigned long)args->stack;
#ifdef DEBUG
- if (ldebug(clone))
- kprintf(LMSG("clone: successful rfork to %ld"),
- (long)p2->p_pid);
+ if (ldebug(clone))
+ kprintf(LMSG("clone: successful rfork to %ld"),
+ (long)p2->p_pid);
#endif
-
- return (0);
+ }
+ return (error);
}
/* XXX move */
#define STACK_SIZE (2 * 1024 * 1024)
#define GUARD_SIZE (4 * PAGE_SIZE)
+/*
+ * MPALMOSTSAFE
+ */
static int
linux_mmap_common(caddr_t linux_addr, size_t linux_len, int linux_prot,
- int linux_flags, int linux_fd, off_t pos, void **res)
+ int linux_flags, int linux_fd, off_t pos, void **res)
{
struct thread *td = curthread;
struct proc *p = td->td_proc;
} else {
flags |= MAP_NOSYNC;
}
+
+ get_mplock();
+
if (linux_flags & LINUX_MAP_GROWSDOWN) {
flags |= MAP_STACK;
/* The linux MAP_GROWSDOWN option does not limit auto
#endif
error = kern_mmap(curproc->p_vmspace, addr, len,
prot, flags, fd, pos, &new);
+ rel_mplock();
if (error == 0)
*res = new;
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_mmap(struct linux_mmap_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_mmap2(struct linux_mmap2_args *args)
{
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_pipe(struct linux_pipe_args *args)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_ioperm(struct linux_ioperm_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_iopl(struct linux_iopl_args *args)
{
struct lwp *lp = td->td_lwp;
int error;
- KKASSERT(lp);
-
if (args->level < 0 || args->level > 3)
return (EINVAL);
if ((error = priv_check(td, PRIV_ROOT)) != 0)
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_modify_ldt(struct linux_modify_ldt_args *uap)
{
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_sigaction(struct linux_sigaction_args *args)
{
linux_to_bsd_sigaction(&linux_act, &act);
}
+ get_mplock();
error = kern_sigaction(args->sig, args->nsa ? &act : NULL,
- args->osa ? &oact : NULL);
+ args->osa ? &oact : NULL);
+ rel_mplock();
if (args->osa != NULL && !error) {
bsd_to_linux_sigaction(&oact, &linux_oact);
* Linux has two extra args, restart and oldmask. We dont use these,
* but it seems that "restart" is actually a context pointer that
* enables the signal to happen with a different register set.
+ *
+ * MPALMOSTSAFE
*/
int
sys_linux_sigsuspend(struct linux_sigsuspend_args *args)
mask.__bits[0] = args->mask;
linux_to_bsd_sigset(&linux_mask, &mask);
+ get_mplock();
error = kern_sigsuspend(&mask);
+ rel_mplock();
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_rt_sigsuspend(struct linux_rt_sigsuspend_args *uap)
{
linux_to_bsd_sigset(&linux_mask, &mask);
+ get_mplock();
error = kern_sigsuspend(&mask);
+ rel_mplock();
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_pause(struct linux_pause_args *args)
{
mask = lp->lwp_sigmask;
+ get_mplock();
error = kern_sigsuspend(&mask);
+ rel_mplock();
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_sigaltstack(struct linux_sigaltstack_args *uap)
{
ss.ss_flags = linux_to_bsd_sigaltstack(linux_ss.ss_flags);
}
+ get_mplock();
error = kern_sigaltstack(uap->uss ? &ss : NULL,
- uap->uoss ? &oss : NULL);
+ uap->uoss ? &oss : NULL);
+ rel_mplock();
if (error == 0 && uap->uoss) {
linux_ss.ss_sp = oss.ss_sp;
* System call prototypes.
*
* DO NOT EDIT-- this file is automatically generated.
- * $DragonFly: src/sys/emulation/linux/i386/linux_proto.h,v 1.19 2008/05/19 10:19:49 corecode Exp $
- * created from DragonFly: src/sys/emulation/linux/i386/syscalls.master,v 1.9 2006/06/05 07:26:10 dillon Exp
*/
#ifndef _LINUX_SYSPROTO_H_
}
#endif
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_ptrace(struct linux_ptrace_args *uap)
{
pid = (pid_t)uap->pid;
addr = (void *)uap->addr;
+ get_mplock();
+
switch (req) {
case PTRACE_TRACEME:
case PTRACE_POKETEXT:
break;
}
+ rel_mplock();
return (error);
}
* System call numbers.
*
* DO NOT EDIT-- this file is automatically generated.
- * $DragonFly: src/sys/emulation/linux/i386/linux_syscall.h,v 1.19 2008/05/19 10:19:49 corecode Exp $
- * created from DragonFly: src/sys/emulation/linux/i386/syscalls.master,v 1.9 2006/06/05 07:26:10 dillon Exp
*/
#define LINUX_SYS_exit 1
* System call switch table.
*
* DO NOT EDIT-- this file is automatically generated.
- * $DragonFly: src/sys/emulation/linux/i386/linux_sysent.c,v 1.19 2008/05/19 10:19:49 corecode Exp $
- * created from DragonFly: src/sys/emulation/linux/i386/syscalls.master,v 1.9 2006/06/05 07:26:10 dillon Exp
*/
#include "opt_compat.h"
* make sure that the user has not modified the
* psl to gain improper privileges or to cause
* a machine fault.
+ *
+ * MPSAFE
*/
int
sys_linux_sigreturn(struct linux_sigreturn_args *args)
* make sure that the user has not modified the
* psl to gain improper privileges or to cause
* a machine fault.
+ *
+ * MPSAFE
*/
int
sys_linux_rt_sigreturn(struct linux_rt_sigreturn_args *args)
* Union of syscall args for messaging.
*
* DO NOT EDIT-- this file is automatically generated.
- * $DragonFly: src/sys/emulation/linux/i386/linux_union.h,v 1.15 2008/05/19 10:19:49 corecode Exp $
- * created from DragonFly: src/sys/emulation/linux/i386/syscalls.master,v 1.9 2006/06/05 07:26:10 dillon Exp
*/
union sysunion {
#include <arch_linux/linux_proto.h>
#include "linux_util.h"
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_creat(struct linux_creat_args *args)
{
if (ldebug(creat))
kprintf(ARGS(creat, "%s, %d"), path, args->mode);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_open(&nd, O_WRONLY | O_CREAT | O_TRUNC,
args->mode, &args->sysmsg_iresult);
}
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_open(struct linux_open_args *args)
{
char *path;
int error, flags;
- KKASSERT(p);
-
if (args->flags & LINUX_O_CREAT) {
error = linux_copyin_path(args->path, &path,
LINUX_PATH_CREATE);
flags |= O_EXCL;
if (args->flags & LINUX_O_NOCTTY)
flags |= O_NOCTTY;
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_open(&nd, flags,
fdrop(fp);
}
}
+ rel_mplock();
#ifdef DEBUG
if (ldebug(open))
kprintf(LMSG("open returns error %d"), error);
return error;
}
+/*
+ * MPSAFE
+ */
int
sys_linux_lseek(struct linux_lseek_args *args)
{
args->fdes, (long)args->off, args->whence);
#endif
error = kern_lseek(args->fdes, args->off, args->whence,
- &args->sysmsg_offset);
+ &args->sysmsg_offset);
return error;
}
+/*
+ * MPSAFE
+ */
int
sys_linux_llseek(struct linux_llseek_args *args)
{
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_readdir(struct linux_readdir_args *args)
{
#define LINUX_DIRBLKSIZ 512
+/*
+ * MPALMOSTSAFE
+ */
static int
getdents_common(struct linux_getdents64_args *args, int is64bit)
{
off_t *cookies = NULL, *cookiep;
int ncookies;
- KKASSERT(p);
-
if ((error = holdvnode(p->p_fd, args->fd, &fp)) != 0)
return (error);
+ get_mplock();
if ((fp->f_flag & FREAD) == 0) {
error = EBADF;
goto done;
kfree(buf, M_TEMP);
done:
+ rel_mplock();
fdrop(fp);
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getdents(struct linux_getdents_args *args)
{
return (getdents_common((struct linux_getdents64_args*)args, 0));
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getdents64(struct linux_getdents64_args *args)
{
/*
* These exist mainly for hooks for doing /compat/linux translation.
+ *
+ * MPALMOSTSAFE
*/
-
int
sys_linux_access(struct linux_access_args *args)
{
if (ldebug(access))
kprintf(ARGS(access, "%s, %d"), path, args->flags);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0)
error = kern_access(&nd, args->flags, 0);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_unlink(struct linux_unlink_args *args)
{
if (ldebug(unlink))
kprintf(ARGS(unlink, "%s"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0)
error = kern_unlink(&nd);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_chdir(struct linux_chdir_args *args)
{
if (ldebug(chdir))
kprintf(ARGS(chdir, "%s"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_chdir(&nd);
nlookup_done(&nd);
}
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_chmod(struct linux_chmod_args *args)
{
if (ldebug(chmod))
kprintf(ARGS(chmod, "%s, %d"), path, args->mode);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0)
error = kern_chmod(&nd, args->mode);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_mkdir(struct linux_mkdir_args *args)
{
if (ldebug(mkdir))
kprintf(ARGS(mkdir, "%s, %d"), path, args->mode);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0)
error = kern_mkdir(&nd, args->mode);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_rmdir(struct linux_rmdir_args *args)
{
if (ldebug(rmdir))
kprintf(ARGS(rmdir, "%s"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0)
error = kern_rmdir(&nd);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_rename(struct linux_rename_args *args)
{
if (ldebug(rename))
kprintf(ARGS(rename, "%s, %s"), from, to);
#endif
+ get_mplock();
error = nlookup_init(&fromnd, from, UIO_SYSSPACE, 0);
if (error == 0) {
error = nlookup_init(&tond, to, UIO_SYSSPACE, 0);
nlookup_done(&tond);
}
nlookup_done(&fromnd);
+ rel_mplock();
linux_free_path(&from);
linux_free_path(&to);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_symlink(struct linux_symlink_args *args)
{
if (ldebug(symlink))
kprintf(ARGS(symlink, "%s, %s"), path, link);
#endif
+ get_mplock();
error = nlookup_init(&nd, link, UIO_SYSSPACE, 0);
if (error == 0) {
mode = ACCESSPERMS & ~td->td_proc->p_fd->fd_cmask;
error = kern_symlink(&nd, path, mode);
}
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
linux_free_path(&link);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_readlink(struct linux_readlink_args *args)
{
kprintf(ARGS(readlink, "%s, %p, %d"), path, (void *)args->buf,
args->count);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0) {
error = kern_readlink(&nd, args->buf, args->count,
&args->sysmsg_iresult);
}
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_truncate(struct linux_truncate_args *args)
{
kprintf(ARGS(truncate, "%s, %ld"), path,
(long)args->length);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0)
error = kern_truncate(&nd, args->length);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_truncate64(struct linux_truncate64_args *args)
{
kprintf(ARGS(truncate64, "%s, %lld"), path,
(off_t)args->length);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0)
error = kern_truncate(&nd, args->length);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_ftruncate(struct linux_ftruncate_args *args)
{
kprintf(ARGS(ftruncate, "%d, %ld"), args->fd,
(long)args->length);
#endif
+ get_mplock();
error = kern_ftruncate(args->fd, args->length);
+ rel_mplock();
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_ftruncate64(struct linux_ftruncate64_args *args)
{
kprintf(ARGS(ftruncate64, "%d, %lld"), args->fd,
(off_t)args->length);
#endif
+ get_mplock();
error = kern_ftruncate(args->fd, args->length);
+ rel_mplock();
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_link(struct linux_link_args *args)
{
if (ldebug(link))
kprintf(ARGS(link, "%s, %s"), path, link);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0) {
error = nlookup_init(&linknd, link, UIO_SYSSPACE, 0);
nlookup_done(&linknd);
}
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
linux_free_path(&link);
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_fdatasync(struct linux_fdatasync_args *uap)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_pread(struct linux_pread_args *uap)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_pwrite(struct linux_pwrite_args *uap)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_oldumount(struct linux_oldumount_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_umount(struct linux_umount_args *args)
{
/*
* fcntl family of syscalls
*/
-
struct l_flock {
l_short l_type;
l_short l_whence;
l_pid_t l_pid;
};
+/*
+ * MPSAFE
+ */
static void
linux_to_bsd_flock(struct l_flock *linux_flock, struct flock *bsd_flock)
{
bsd_flock->l_pid = (pid_t)linux_flock->l_pid;
}
+/*
+ * MPSAFE
+ */
static void
bsd_to_linux_flock(struct flock *bsd_flock, struct l_flock *linux_flock)
{
l_pid_t l_pid;
};
+/*
+ * MPSAFE
+ */
static void
linux_to_bsd_flock64(struct l_flock64 *linux_flock, struct flock *bsd_flock)
{
bsd_flock->l_pid = (pid_t)linux_flock->l_pid;
}
+/*
+ * MPSAFE
+ */
static void
bsd_to_linux_flock64(struct flock *bsd_flock, struct l_flock64 *linux_flock)
{
}
#endif /* __i386__ */
+/*
+ * MPSAFE
+ */
static int
linux_fcntl_common(struct linux_fcntl64_args *args)
{
return (EINVAL);
}
+ /* MPSAFE */
error = kern_fcntl(args->fd, cmd, &dat, p->p_ucred);
if (error == 0) {
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_fcntl(struct linux_fcntl_args *args)
{
}
#if defined(__i386__)
+/*
+ * MPSAFE
+ */
int
sys_linux_fcntl64(struct linux_fcntl64_args *args)
{
return (error);
linux_to_bsd_flock64(&linux_flock, &dat.fc_flock);
+ /* MPSAFE */
error = kern_fcntl(args->fd, cmd, &dat, curproc->p_ucred);
if (error == 0 && args->cmd == LINUX_F_GETLK64) {
}
#endif /* __i386__ */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_chown(struct linux_chown_args *args)
{
if (ldebug(chown))
kprintf(ARGS(chown, "%s, %d, %d"), path, args->uid, args->gid);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0)
error = kern_chown(&nd, args->uid, args->gid);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_lchown(struct linux_lchown_args *args)
{
if (ldebug(lchown))
kprintf(ARGS(lchown, "%s, %d, %d"), path, args->uid, args->gid);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0)
error = kern_chown(&nd, args->uid, args->gid);
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
*
* Use vfs vnode-to-name reverse cache; if that fails, fall back
* to reading directory contents.
+ *
+ * MPALMOSTSAFE
*/
-
int
sys_linux_getcwd(struct linux_getcwd_args *args)
{
buflen = MAXPATHLEN;
buf = kmalloc(buflen, M_TEMP, M_WAITOK);
+ get_mplock();
bp = kern_getcwd(buf, buflen, &error);
+ rel_mplock();
if (error == 0) {
buflen = strlen(bp) + 1;
error = copyout(bp, args->buf, buflen);
/*
* main ioctl syscall function
+ *
+ * MPALMOSTSAFE
*/
-
int
sys_linux_ioctl(struct linux_ioctl_args *args)
{
+ int error;
+
#ifdef DEBUG
if (ldebug(ioctl))
kprintf(ARGS(ioctl, "%d, %04x, *"), args->fd, args->cmd);
#endif
- return (mapped_ioctl(args->fd, args->cmd, (caddr_t)args->arg,
- &linux_ioctl_map, &args->sysmsg));
+ get_mplock();
+ error = mapped_ioctl(args->fd, args->cmd, (caddr_t)args->arg,
+ &linux_ioctl_map, &args->sysmsg);
+ rel_mplock();
+ return (error);
}
SYSINIT (linux_ioctl_register, SI_BOOT2_KLD, SI_ORDER_MIDDLE,
l_ushort seq;
};
+/*
+ * MPSAFE
+ */
static void
linux_to_bsd_ipc_perm(struct l_ipc_perm *lpp, struct ipc_perm *bpp)
{
bpp->seq = lpp->seq;
}
-
+/*
+ * MPSAFE
+ */
static void
bsd_to_linux_ipc_perm(struct ipc_perm *bpp, struct l_ipc_perm *lpp)
{
void *private3;
};
+/*
+ * MPSAFE
+ */
static void
linux_to_bsd_semid_ds(struct l_semid_ds *lsp, struct semid_ds *bsp)
{
bsp->sem_base = lsp->sem_base;
}
+/*
+ * MPSAFE
+ */
static void
bsd_to_linux_semid_ds(struct semid_ds *bsp, struct l_semid_ds *lsp)
{
lsp->sem_base = bsp->sem_base;
}
+/*
+ * MPSAFE
+ */
static void
linux_to_bsd_shmid_ds(struct l_shmid_ds *lsp, struct shmid_ds *bsp)
{
bsp->shm_internal = lsp->private3; /* this goes (yet) SOS */
}
+/*
+ * MPSAFE
+ */
static void
bsd_to_linux_shmid_ds(struct shmid_ds *bsp, struct l_shmid_ds *lsp)
{
lsp->private3 = bsp->shm_internal; /* this goes (yet) SOS */
}
+/*
+ * MPSAFE
+ */
int
linux_semop(struct linux_semop_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_semget(struct linux_semget_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_semctl(struct linux_semctl_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_msgsnd(struct linux_msgsnd_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_msgrcv(struct linux_msgrcv_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_msgget(struct linux_msgget_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_msgctl(struct linux_msgctl_args *args)
{
return ((args->cmd == LINUX_IPC_RMID && error == EINVAL) ? 0 : error);
}
+/*
+ * MPSAFE
+ */
int
linux_shmat(struct linux_shmat_args *args)
{
return 0;
}
+/*
+ * MPSAFE
+ */
int
linux_shmdt(struct linux_shmdt_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_shmget(struct linux_shmget_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_shmctl(struct linux_shmctl_args *args)
{
char _f[22]; /* Pads structure to 64 bytes */
};
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_sysinfo(struct linux_sysinfo_args *args)
{
struct l_sysinfo sysinfo;
vm_object_t object;
- int i;
struct timespec ts;
+ int error;
+ int i;
/* Uptime is copied out of print_uptime() in kern_shutdown.c */
getnanouptime(&ts);
sysinfo.totalram = Maxmem * PAGE_SIZE;
sysinfo.freeram = sysinfo.totalram - vmstats.v_wire_count * PAGE_SIZE;
+ get_mplock();
sysinfo.sharedram = 0;
for (object = TAILQ_FIRST(&vm_object_list); object != NULL;
object = TAILQ_NEXT(object, object_list))
sysinfo.totalswap = swapblist->bl_blocks * 1024;
sysinfo.freeswap = swapblist->bl_root->u.bmu_avail * PAGE_SIZE;
}
+ rel_mplock();
sysinfo.procs = 20; /* Hack */
- return copyout(&sysinfo, (caddr_t)args->info, sizeof(sysinfo));
+ error = copyout(&sysinfo, (caddr_t)args->info, sizeof(sysinfo));
+ return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_alarm(struct linux_alarm_args *args)
{
struct itimerval it, old_it;
struct timeval tv;
- KKASSERT(p);
-
#ifdef DEBUG
if (ldebug(alarm))
kprintf(ARGS(alarm, "%u"), args->secs);
it.it_value.tv_usec = 0;
it.it_interval.tv_sec = 0;
it.it_interval.tv_usec = 0;
+ get_mplock();
crit_enter();
old_it = p->p_realtimer;
getmicrouptime(&tv);
}
p->p_realtimer = it;
crit_exit();
+ rel_mplock();
if (timevalcmp(&old_it.it_value, &tv, >)) {
timevalsub(&old_it.it_value, &tv);
if (old_it.it_value.tv_usec != 0)
return 0;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_brk(struct linux_brk_args *args)
{
vm_offset_t new, old;
struct obreak_args bsd_args;
- KKASSERT(p);
+ get_mplock();
vm = p->p_vmspace;
#ifdef DEBUG
if (ldebug(brk))
args->sysmsg_result = (long)new;
else
args->sysmsg_result = (long)old;
+ rel_mplock();
return 0;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_uselib(struct linux_uselib_args *args)
{
int locked;
char *path;
- KKASSERT(td->td_proc);
p = td->td_proc;
error = linux_copyin_path(args->library, &path, LINUX_PATH_EXISTS);
locked = 0;
vp = NULL;
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
nd.nl_flags |= NLC_EXEC;
if (error == 0)
(vm_offset_t)a_out + PAGE_SIZE);
}
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_select(struct linux_select_args *args)
{
return error;
}
+/*
+ * MPSAFE
+ */
int
sys_linux_mremap(struct linux_mremap_args *args)
{
#define LINUX_MS_INVALIDATE 0x0002
#define LINUX_MS_SYNC 0x0004
+/*
+ * MPSAFE
+ */
int
sys_linux_msync(struct linux_msync_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_time(struct linux_time_args *args)
{
#define CONVTCK(r) (r.tv_sec * CLK_TCK + r.tv_usec / (1000000 / CLK_TCK))
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_times(struct linux_times_args *args)
{
struct rusage ru;
int error;
- KKASSERT(p);
#ifdef DEBUG
if (ldebug(times))
kprintf(ARGS(times, "*"));
#endif
+ get_mplock();
calcru_proc(p, &ru);
+ rel_mplock();
tms.tms_utime = CONVTCK(ru.ru_utime);
tms.tms_stime = CONVTCK(ru.ru_stime);
return 0;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_newuname(struct linux_newuname_args *args)
{
kprintf(ARGS(newuname, "*"));
#endif
+ get_mplock();
osname = linux_get_osname(td);
osrelease = linux_get_osrelease(td);
strncpy(utsname.version, version, LINUX_MAX_UTSNAME-1);
strncpy(utsname.machine, machine, LINUX_MAX_UTSNAME-1);
strncpy(utsname.domainname, domainname, LINUX_MAX_UTSNAME-1);
+ rel_mplock();
return (copyout(&utsname, (caddr_t)args->buf, sizeof(utsname)));
}
l_time_t l_modtime;
};
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_utime(struct linux_utime_args *args)
{
tv[1].tv_sec = lut.l_modtime;
tv[1].tv_usec = 0;
}
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0)
error = kern_utimes(&nd, args->times ? tv : NULL);
nlookup_done(&nd);
+ rel_mplock();
cleanup:
linux_free_path(&path);
return (error);
#define __WCLONE 0x80000000
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_waitpid(struct linux_waitpid_args *args)
{
options |= WLINUXCLONE;
error = kern_wait(args->pid, args->status ? &status : NULL, options,
- NULL, &args->sysmsg_result);
+ NULL, &args->sysmsg_result);
if (error == 0 && args->status) {
status &= 0xffff;
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_wait4(struct linux_wait4_args *args)
{
struct rusage rusage;
int error, options, status;
- KKASSERT(lp);
-
#ifdef DEBUG
if (ldebug(wait4))
kprintf(ARGS(wait4, "%d, %p, %d, %p"),
options |= WLINUXCLONE;
error = kern_wait(args->pid, args->status ? &status : NULL, options,
- args->rusage ? &rusage : NULL, &args->sysmsg_result);
+ args->rusage ? &rusage : NULL, &args->sysmsg_result);
if (error == 0)
lwp_delsig(lp, SIGCHLD);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_mknod(struct linux_mknod_args *args)
{
kprintf(ARGS(mknod, "%s, %d, %d"),
path, args->mode, args->dev);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0) {
if (args->mode & S_IFIFO) {
}
}
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
/*
* UGH! This is just about the dumbest idea I've ever heard!!
+ *
+ * MPSAFE
*/
int
sys_linux_personality(struct linux_personality_args *args)
/*
* Wrappers for get/setitimer for debugging..
+ *
+ * MPSAFE
*/
int
sys_linux_setitimer(struct linux_setitimer_args *args)
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getitimer(struct linux_getitimer_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_nice(struct linux_nice_args *args)
{
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_setgroups(struct linux_setgroups_args *args)
{
gid_t *bsd_gidset;
int ngrp, error;
- KKASSERT(p);
-
ngrp = args->gidsetsize;
oldcred = p->p_ucred;
if ((error = priv_check_cred(oldcred, PRIV_CRED_SETGROUPS, 0)) != 0)
return (error);
- if (ngrp >= NGROUPS)
+ if ((u_int)ngrp >= NGROUPS)
return (EINVAL);
+ get_mplock();
newcred = crdup(oldcred);
if (ngrp > 0) {
error = copyin((caddr_t)args->grouplist, linux_gidset,
ngrp * sizeof(l_gid_t));
if (error) {
crfree(newcred);
+ rel_mplock();
return (error);
}
setsugid();
p->p_ucred = newcred;
crfree(oldcred);
+ rel_mplock();
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getgroups(struct linux_getgroups_args *args)
{
gid_t *bsd_gidset;
int bsd_gidsetsz, ngrp, error;
- KKASSERT(p);
-
cred = p->p_ucred;
bsd_gidset = cred->cr_groups;
bsd_gidsetsz = cred->cr_ngroups - 1;
return (0);
}
- if (ngrp < bsd_gidsetsz)
+ if ((u_int)ngrp < bsd_gidsetsz)
return (EINVAL);
ngrp = 0;
ngrp++;
}
- if ((error = copyout(linux_gidset, (caddr_t)args->grouplist,
- ngrp * sizeof(l_gid_t))))
+ if ((error = copyout(linux_gidset, args->grouplist,
+ ngrp * sizeof(l_gid_t)))) {
return (error);
+ }
args->sysmsg_result = ngrp;
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_setrlimit(struct linux_setrlimit_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_old_getrlimit(struct linux_old_getrlimit_args *args)
{
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getrlimit(struct linux_getrlimit_args *args)
{
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_sched_setscheduler(struct linux_sched_setscheduler_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_sched_getscheduler(struct linux_sched_getscheduler_args *args)
{
return error;
}
+/*
+ * MPSAFE
+ */
int
sys_linux_sched_get_priority_max(struct linux_sched_get_priority_max_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_sched_get_priority_min(struct linux_sched_get_priority_min_args *args)
{
#define REBOOT_CAD_OFF 0
#define REBOOT_HALT 0xcdef0123
+/*
+ * MPSAFE
+ */
int
sys_linux_reboot(struct linux_reboot_args *args)
{
* linux_getuid() - MP SAFE
*/
+/*
+ * MPSAFE
+ */
int
sys_linux_getpid(struct linux_getpid_args *args)
{
struct thread *td = curthread;
struct proc *p = td->td_proc;
- KKASSERT(p);
-
args->sysmsg_result = p->p_pid;
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getgid(struct linux_getgid_args *args)
{
struct thread *td = curthread;
struct proc *p = td->td_proc;
- KKASSERT(p);
-
args->sysmsg_result = p->p_ucred->cr_rgid;
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getuid(struct linux_getuid_args *args)
{
struct thread *td = curthread;
struct proc *p = td->td_proc;
- KKASSERT(p);
-
args->sysmsg_result = p->p_ucred->cr_ruid;
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getsid(struct linux_getsid_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
linux_nosys(struct nosys_args *args)
{
#include <sys/signalvar.h>
#include <sys/sysproto.h>
#include <sys/kern_syscall.h>
-
+#include <sys/thread.h>
+#include <sys/thread2.h>
#include <arch_linux/linux.h>
#include <arch_linux/linux_proto.h>
#include "linux_signal.h"
lsa->lsa_flags |= LINUX_SA_NOMASK;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_signal(struct linux_signal_args *args)
{
sig = args->sig;
}
+ get_mplock();
error = kern_sigaction(sig, &nsa, &osa);
+ rel_mplock();
bsd_to_linux_sigaction(&osa, &linux_osa);
args->sysmsg_result = (int) linux_osa.lsa_handler;
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_rt_sigaction(struct linux_rt_sigaction_args *args)
{
sig = args->sig;
}
+ get_mplock();
error = kern_sigaction(sig, args->act ? &nsa : NULL,
- args->oact ? &osa : NULL);
+ args->oact ? &osa : NULL);
+ rel_mplock();
if (error == 0 && args->oact) {
bsd_to_linux_sigaction(&osa, &linux_osa);
}
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_sigprocmask(struct linux_sigprocmask_args *args)
{
}
how = linux_to_bsd_sigprocmask(args->how);
+ get_mplock();
error = kern_sigprocmask(how, args->mask ? &set : NULL,
- args->omask ? &oset : NULL);
+ args->omask ? &oset : NULL);
+ rel_mplock();
if (error == 0 && args->omask) {
bsd_to_linux_sigset(&oset, &linux_oset);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_rt_sigprocmask(struct linux_rt_sigprocmask_args *args)
{
}
how = linux_to_bsd_sigprocmask(args->how);
+ get_mplock();
error = kern_sigprocmask(how, args->mask ? &set : NULL,
- args->omask ? &oset : NULL);
+ args->omask ? &oset : NULL);
+ rel_mplock();
if (error == 0 && args->omask) {
bsd_to_linux_sigset(&oset, &linux_oset);
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_sgetmask(struct linux_sgetmask_args *args)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_ssetmask(struct linux_ssetmask_args *args)
{
LINUX_SIGEMPTYSET(lset);
lset.__bits[0] = args->mask;
linux_to_bsd_sigset(&lset, &bset);
+ crit_enter();
lp->lwp_sigmask = bset;
SIG_CANTMASK(lp->lwp_sigmask);
+ crit_exit();
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_sigpending(struct linux_sigpending_args *args)
{
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_kill(struct linux_kill_args *args)
{
else
sig = args->signum;
+ get_mplock();
error = kern_kill(sig, args->pid, -1);
+ rel_mplock();
return(error);
}
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_socketcall(struct linux_socketcall_args *args)
{
void *arg = (void *)args->args;
+ get_mplock();
+
switch (args->what) {
case LINUX_SOCKET:
return (linux_socket(arg, &args->sysmsg_result));
case LINUX_RECVMSG:
return (linux_recvmsg(arg, &args->sysmsg_szresult));
}
+ rel_mplock();
uprintf("LINUX: 'socket' typ=%d not implemented\n", args->what);
return (ENOSYS);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_newstat(struct linux_newstat_args *args)
{
if (ldebug(newstat))
kprintf(ARGS(newstat, "%s, *"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_stat(&nd, &buf);
error = newstat_copyout(&buf, args->buf);
nlookup_done(&nd);
}
+ rel_mplock();
linux_free_path(&path);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_newlstat(struct linux_newlstat_args *args)
{
if (ldebug(newlstat))
kprintf(ARGS(newlstat, "%s, *"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0) {
error = kern_stat(&nd, &sb);
error = newstat_copyout(&sb, args->buf);
nlookup_done(&nd);
}
+ rel_mplock();
linux_free_path(&path);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_newfstat(struct linux_newfstat_args *args)
{
if (ldebug(newfstat))
kprintf(ARGS(newfstat, "%d, *"), args->fd);
#endif
+ get_mplock();
error = kern_fstat(args->fd, &buf);
+ rel_mplock();
if (error == 0)
error = newstat_copyout(&buf, args->buf);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_statfs(struct linux_statfs_args *args)
{
if (ldebug(statfs))
kprintf(ARGS(statfs, "%s, *"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0)
error = kern_statfs(&nd, &statfs);
error = EINVAL;
}
nlookup_done(&nd);
+ rel_mplock();
if (error == 0)
error = statfs_copyout(&statfs, args->buf, (l_int)namelen);
linux_free_path(&path);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_fstatfs(struct linux_fstatfs_args *args)
{
if (ldebug(fstatfs))
kprintf(ARGS(fstatfs, "%d, *"), args->fd);
#endif
+ get_mplock();
if ((error = kern_fstatfs(args->fd, &statfs)) != 0)
return (error);
if ((error = holdvnode(p->p_fd, args->fd, &fp)) != 0)
return (error);
error = vn_get_namelen((struct vnode *)fp->f_data, &namelen);
+ rel_mplock();
fdrop(fp);
if (error == 0)
error = statfs_copyout(&statfs, args->buf, (l_int)namelen);
char f_fpack[6];
};
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_ustat(struct linux_ustat_args *args)
{
* cdev_t returned from previous syscalls. Just return a bzeroed
* ustat in that case.
*/
+ get_mplock();
dev = udev2dev(makeudev(args->dev >> 8, args->dev & 0xFF), 0);
if (dev != NULL && vfinddev(dev, VCHR, &vp)) {
if (vp->v_mount == NULL) {
vrele(vp);
- return (EINVAL);
+ error = EINVAL;
+ goto done;
}
stat = &(vp->v_mount->mnt_stat);
error = VFS_STATFS(vp->v_mount, stat, curproc->p_ucred);
vrele(vp);
- if (error) {
- return (error);
+ if (error == 0) {
+ lu.f_tfree = stat->f_bfree;
+ lu.f_tinode = stat->f_ffree;
}
- lu.f_tfree = stat->f_bfree;
- lu.f_tinode = stat->f_ffree;
+ } else {
+ error = 0;
}
- return (copyout(&lu, args->ubuf, sizeof(lu)));
+done:
+ rel_mplock();
+ if (error == 0)
+ error = copyout(&lu, args->ubuf, sizeof(lu));
+ return (error);
}
#if defined(__i386__)
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_stat64(struct linux_stat64_args *args)
{
if (ldebug(stat64))
kprintf(ARGS(stat64, "%s, *"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_stat(&nd, &buf);
- if (error == 0)
- error = stat64_copyout(&buf, args->statbuf);
nlookup_done(&nd);
}
+ rel_mplock();
+ if (error == 0)
+ error = stat64_copyout(&buf, args->statbuf);
linux_free_path(&path);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_lstat64(struct linux_lstat64_args *args)
{
if (ldebug(lstat64))
kprintf(ARGS(lstat64, "%s, *"), path);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0) {
error = kern_stat(&nd, &sb);
- if (error == 0)
- error = stat64_copyout(&sb, args->statbuf);
nlookup_done(&nd);
}
+ rel_mplock();
+ if (error == 0)
+ error = stat64_copyout(&sb, args->statbuf);
linux_free_path(&path);
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_fstat64(struct linux_fstat64_args *args)
{
if (ldebug(fstat64))
kprintf(ARGS(fstat64, "%d, *"), args->fd);
#endif
+ get_mplock();
error = kern_fstat(args->fd, &buf);
+ rel_mplock();
if (error == 0)
error = stat64_copyout(&buf, args->statbuf);
return (0);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_sysctl(struct linux_sysctl_args *args)
{
return (error);
}
+ get_mplock();
+
switch (mib[0]) {
case LINUX_CTL_KERN:
- if (la.nlen < 2)
+ if (la.nlen < 2) {
+ error = ENOTDIR;
break;
+ }
switch (mib[1]) {
case LINUX_KERN_VERSION:
- kfree(mib, M_TEMP);
- return (handle_string(&la, version));
+ error = handle_string(&la, version);
+ break;
default:
+ error = ENOTDIR;
break;
}
break;
default:
+ error = ENOTDIR;
break;
}
+ rel_mplock();
- kprintf("linux: sysctl: unhandled name=");
- for (i = 0; i < la.nlen; i++)
- kprintf("%c%d", (i) ? ',' : '{', mib[i]);
- kprintf("}\n");
-
- kfree(mib, M_TEMP);
- return (ENOTDIR);
+ if (error == ENOTDIR && mib) {
+ kprintf("linux: sysctl: unhandled name=");
+ for (i = 0; i < la.nlen; i++)
+ kprintf("%c%d", (i) ? ',' : '{', mib[i]);
+ kprintf("}\n");
+ }
+ if (mib)
+ kfree(mib, M_TEMP);
+ return (error);
}
#define CAST_NOCHG(x) ((x == 0xFFFF) ? -1 : x)
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_chown16(struct linux_chown16_args *args)
{
kprintf(ARGS(chown16, "%s, %d, %d"), path, args->uid,
args->gid);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, NLC_FOLLOW);
if (error == 0) {
error = kern_chown(&nd, CAST_NOCHG(args->uid),
CAST_NOCHG(args->gid));
}
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_lchown16(struct linux_lchown16_args *args)
{
kprintf(ARGS(lchown16, "%s, %d, %d"), path, args->uid,
args->gid);
#endif
+ get_mplock();
error = nlookup_init(&nd, path, UIO_SYSSPACE, 0);
if (error == 0) {
error = kern_chown(&nd, CAST_NOCHG(args->uid),
CAST_NOCHG(args->gid));
}
nlookup_done(&nd);
+ rel_mplock();
linux_free_path(&path);
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_linux_setgroups16(struct linux_setgroups16_args *args)
{
if ((error = priv_check_cred(oldcred, PRIV_CRED_SETGROUPS, 0)) != 0)
return (error);
- if (ngrp >= NGROUPS)
+ if ((u_int)ngrp >= NGROUPS)
return (EINVAL);
+ get_mplock();
newcred = crdup(oldcred);
if (ngrp > 0) {
error = copyin((caddr_t)args->gidset, linux_gidset,
ngrp * sizeof(l_gid16_t));
if (error) {
crfree(newcred);
- return (error);
+ goto done;
}
newcred->cr_ngroups = ngrp + 1;
setsugid();
p->p_ucred = newcred;
crfree(oldcred);
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getgroups16(struct linux_getgroups16_args *args)
{
return (0);
}
- if (ngrp < bsd_gidsetsz)
+ if ((u_int)ngrp < (u_int)bsd_gidsetsz)
return (EINVAL);
ngrp = 0;
}
error = copyout(linux_gidset, (caddr_t)args->gidset,
- ngrp * sizeof(l_gid16_t));
+ ngrp * sizeof(l_gid16_t));
if (error)
return (error);
* linux_getuid16() - MP SAFE
*/
+/*
+ * MPSAFE
+ */
int
sys_linux_getgid16(struct linux_getgid16_args *args)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getuid16(struct linux_getuid16_args *args)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_getegid16(struct linux_getegid16_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_geteuid16(struct linux_geteuid16_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_setgid16(struct linux_setgid16_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_setuid16(struct linux_setuid16_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_setregid16(struct linux_setregid16_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_setreuid16(struct linux_setreuid16_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_setresgid16(struct linux_setresgid16_args *args)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_linux_setresuid16(struct linux_setresuid16_args *args)
{
* PRIV_VM_RESIDENT credentials) can do this. This
* will snapshot the vmspace and cause future exec's of the specified binary
* to use the snapshot directly rather then load & relocate a new copy.
+ *
+ * MPALMOSTSAFE
*/
int
sys_exec_sys_register(struct exec_sys_register_args *uap)
p = curproc;
if ((error = priv_check_cred(p->p_ucred, PRIV_VM_RESIDENT, 0)) != 0)
return(error);
- if ((vp = p->p_textvp) == NULL)
+
+ get_mplock();
+
+ if ((vp = p->p_textvp) == NULL) {
+ rel_mplock();
return(ENOENT);
- if (vp->v_resident)
+ }
+ if (vp->v_resident) {
+ rel_mplock();
return(EEXIST);
+ }
vhold(vp);
vmres = kmalloc(sizeof(*vmres), M_EXEC_RES, M_WAITOK);
vp->v_resident = vmres;
TAILQ_INSERT_TAIL(&exec_res_list, vmres, vr_link);
lockmgr(&exec_list_lock, LK_RELEASE);
+ rel_mplock();
return(0);
}
* Unregister the specified id. If an id of -1 is used unregister
* the registration associated with the current process. An id of -2
* unregisters everything.
+ *
+ * MPALMOSTSAFE
*/
int
sys_exec_sys_unregister(struct exec_sys_unregister_args *uap)
/*
* If id is -1, unregister ourselves
*/
+ get_mplock();
if ((id = uap->id) == -1 && p->p_textvp && p->p_textvp->v_resident)
id = p->p_textvp->v_resident->vr_id;
}
}
lockmgr(&exec_list_lock, LK_RELEASE);
+ rel_mplock();
if (error == 0)
uap->sysmsg_result = count;
return(error);
{ 0, (sy_call_t *)sys_nosys }, /* 0 = syscall */
{ AS(exit_args), (sy_call_t *)sys_exit }, /* 1 = exit */
{ 0, (sy_call_t *)sys_fork }, /* 2 = fork */
- { SYF_MPSAFE | AS(read_args), (sy_call_t *)sys_read }, /* 3 = read */
- { SYF_MPSAFE | AS(write_args), (sy_call_t *)sys_write }, /* 4 = write */
+ { AS(read_args), (sy_call_t *)sys_read }, /* 3 = read */
+ { AS(write_args), (sy_call_t *)sys_write }, /* 4 = write */
{ AS(open_args), (sy_call_t *)sys_open }, /* 5 = open */
- { SYF_MPSAFE | AS(close_args), (sy_call_t *)sys_close }, /* 6 = close */
+ { AS(close_args), (sy_call_t *)sys_close }, /* 6 = close */
{ AS(wait_args), (sy_call_t *)sys_wait4 }, /* 7 = wait4 */
{ compat(AS(ocreat_args),creat) }, /* 8 = old creat */
{ AS(link_args), (sy_call_t *)sys_link }, /* 9 = link */
{ AS(mount_args), (sy_call_t *)sys_mount }, /* 21 = mount */
{ AS(unmount_args), (sy_call_t *)sys_unmount }, /* 22 = unmount */
{ AS(setuid_args), (sy_call_t *)sys_setuid }, /* 23 = setuid */
- { SYF_MPSAFE | 0, (sy_call_t *)sys_getuid }, /* 24 = getuid */
- { SYF_MPSAFE | 0, (sy_call_t *)sys_geteuid }, /* 25 = geteuid */
+ { 0, (sy_call_t *)sys_getuid }, /* 24 = getuid */
+ { 0, (sy_call_t *)sys_geteuid }, /* 25 = geteuid */
{ AS(ptrace_args), (sy_call_t *)sys_ptrace }, /* 26 = ptrace */
{ AS(recvmsg_args), (sy_call_t *)sys_recvmsg }, /* 27 = recvmsg */
{ AS(sendmsg_args), (sy_call_t *)sys_sendmsg }, /* 28 = sendmsg */
{ compat(AS(ostat_args),stat) }, /* 38 = old stat */
{ 0, (sy_call_t *)sys_getppid }, /* 39 = getppid */
{ compat(AS(olstat_args),lstat) }, /* 40 = old lstat */
- { SYF_MPSAFE | AS(dup_args), (sy_call_t *)sys_dup }, /* 41 = dup */
+ { AS(dup_args), (sy_call_t *)sys_dup }, /* 41 = dup */
{ 0, (sy_call_t *)sys_pipe }, /* 42 = pipe */
{ 0, (sy_call_t *)sys_getegid }, /* 43 = getegid */
{ AS(profil_args), (sy_call_t *)sys_profil }, /* 44 = profil */
{ AS(ktrace_args), (sy_call_t *)sys_ktrace }, /* 45 = ktrace */
{ 0, (sy_call_t *)sys_nosys }, /* 46 = obsolete freebsd3_sigaction */
- { SYF_MPSAFE | 0, (sy_call_t *)sys_getgid }, /* 47 = getgid */
+ { 0, (sy_call_t *)sys_getgid }, /* 47 = getgid */
{ 0, (sy_call_t *)sys_nosys }, /* 48 = obsolete freebsd3_sigprocmask */
{ AS(getlogin_args), (sy_call_t *)sys_getlogin }, /* 49 = getlogin */
{ AS(setlogin_args), (sy_call_t *)sys_setlogin }, /* 50 = setlogin */
{ AS(symlink_args), (sy_call_t *)sys_symlink }, /* 57 = symlink */
{ AS(readlink_args), (sy_call_t *)sys_readlink }, /* 58 = readlink */
{ AS(execve_args), (sy_call_t *)sys_execve }, /* 59 = execve */
- { SYF_MPSAFE | AS(umask_args), (sy_call_t *)sys_umask }, /* 60 = umask */
+ { AS(umask_args), (sy_call_t *)sys_umask }, /* 60 = umask */
{ AS(chroot_args), (sy_call_t *)sys_chroot }, /* 61 = chroot */
{ compat(AS(ofstat_args),fstat) }, /* 62 = old fstat */
{ compat(AS(getkerninfo_args),getkerninfo) }, /* 63 = old getkerninfo */
{ AS(mincore_args), (sy_call_t *)sys_mincore }, /* 78 = mincore */
{ AS(getgroups_args), (sy_call_t *)sys_getgroups }, /* 79 = getgroups */
{ AS(setgroups_args), (sy_call_t *)sys_setgroups }, /* 80 = setgroups */
- { SYF_MPSAFE | 0, (sy_call_t *)sys_getpgrp }, /* 81 = getpgrp */
+ { 0, (sy_call_t *)sys_getpgrp }, /* 81 = getpgrp */
{ AS(setpgid_args), (sy_call_t *)sys_setpgid }, /* 82 = setpgid */
{ AS(setitimer_args), (sy_call_t *)sys_setitimer }, /* 83 = setitimer */
{ compat(0,wait) }, /* 84 = old wait */
{ AS(getitimer_args), (sy_call_t *)sys_getitimer }, /* 86 = getitimer */
{ compat(AS(gethostname_args),gethostname) }, /* 87 = old gethostname */
{ compat(AS(sethostname_args),sethostname) }, /* 88 = old sethostname */
- { SYF_MPSAFE | 0, (sy_call_t *)sys_getdtablesize }, /* 89 = getdtablesize */
- { SYF_MPSAFE | AS(dup2_args), (sy_call_t *)sys_dup2 }, /* 90 = dup2 */
+ { 0, (sy_call_t *)sys_getdtablesize }, /* 89 = getdtablesize */
+ { AS(dup2_args), (sy_call_t *)sys_dup2 }, /* 90 = dup2 */
{ 0, (sy_call_t *)sys_nosys }, /* 91 = getdopt */
- { SYF_MPSAFE | AS(fcntl_args), (sy_call_t *)sys_fcntl }, /* 92 = fcntl */
+ { AS(fcntl_args), (sy_call_t *)sys_fcntl }, /* 92 = fcntl */
{ AS(select_args), (sy_call_t *)sys_select }, /* 93 = select */
{ 0, (sy_call_t *)sys_nosys }, /* 94 = setdopt */
{ AS(fsync_args), (sy_call_t *)sys_fsync }, /* 95 = fsync */
{ compat(AS(orecvmsg_args),recvmsg) }, /* 113 = old recvmsg */
{ compat(AS(osendmsg_args),sendmsg) }, /* 114 = old sendmsg */
{ 0, (sy_call_t *)sys_nosys }, /* 115 = obsolete vtrace */
- { SYF_MPSAFE | AS(gettimeofday_args), (sy_call_t *)sys_gettimeofday }, /* 116 = gettimeofday */
+ { AS(gettimeofday_args), (sy_call_t *)sys_gettimeofday }, /* 116 = gettimeofday */
{ AS(getrusage_args), (sy_call_t *)sys_getrusage }, /* 117 = getrusage */
{ AS(getsockopt_args), (sy_call_t *)sys_getsockopt }, /* 118 = getsockopt */
{ 0, (sy_call_t *)sys_nosys }, /* 119 = resuba */
- { SYF_MPSAFE | AS(readv_args), (sy_call_t *)sys_readv }, /* 120 = readv */
- { SYF_MPSAFE | AS(writev_args), (sy_call_t *)sys_writev }, /* 121 = writev */
+ { AS(readv_args), (sy_call_t *)sys_readv }, /* 120 = readv */
+ { AS(writev_args), (sy_call_t *)sys_writev }, /* 121 = writev */
{ AS(settimeofday_args), (sy_call_t *)sys_settimeofday }, /* 122 = settimeofday */
{ AS(fchown_args), (sy_call_t *)sys_fchown }, /* 123 = fchown */
{ AS(fchmod_args), (sy_call_t *)sys_fchmod }, /* 124 = fchmod */
{ compat(AS(ogetpeername_args),getpeername) }, /* 141 = old getpeername */
{ compat(0,gethostid) }, /* 142 = old gethostid */
{ compat(AS(osethostid_args),sethostid) }, /* 143 = old sethostid */
- { compat(SYF_MPSAFE | AS(ogetrlimit_args),getrlimit) }, /* 144 = old getrlimit */
- { compat(SYF_MPSAFE | AS(osetrlimit_args),setrlimit) }, /* 145 = old setrlimit */
+ { compat(AS(ogetrlimit_args),getrlimit) }, /* 144 = old getrlimit */
+ { compat(AS(osetrlimit_args),setrlimit) }, /* 145 = old setrlimit */
{ compat(AS(okillpg_args),killpg) }, /* 146 = old killpg */
{ 0, (sy_call_t *)sys_setsid }, /* 147 = setsid */
{ AS(quotactl_args), (sy_call_t *)sys_quotactl }, /* 148 = quotactl */
{ AS(msgsys_args), (sy_call_t *)sys_msgsys }, /* 170 = msgsys */
{ AS(shmsys_args), (sy_call_t *)sys_shmsys }, /* 171 = shmsys */
{ 0, (sy_call_t *)sys_nosys }, /* 172 = nosys */
- { SYF_MPSAFE | AS(extpread_args), (sy_call_t *)sys_extpread }, /* 173 = extpread */
- { SYF_MPSAFE | AS(extpwrite_args), (sy_call_t *)sys_extpwrite }, /* 174 = extpwrite */
+ { AS(extpread_args), (sy_call_t *)sys_extpread }, /* 173 = extpread */
+ { AS(extpwrite_args), (sy_call_t *)sys_extpwrite }, /* 174 = extpwrite */
{ 0, (sy_call_t *)sys_nosys }, /* 175 = nosys */
{ AS(ntp_adjtime_args), (sy_call_t *)sys_ntp_adjtime }, /* 176 = ntp_adjtime */
{ 0, (sy_call_t *)sys_nosys }, /* 177 = sfork */
{ 0, (sy_call_t *)sys_nosys }, /* 286 = nosys */
{ 0, (sy_call_t *)sys_nosys }, /* 287 = nosys */
{ 0, (sy_call_t *)sys_nosys }, /* 288 = nosys */
- { SYF_MPSAFE | AS(extpreadv_args), (sy_call_t *)sys_extpreadv }, /* 289 = extpreadv */
- { SYF_MPSAFE | AS(extpwritev_args), (sy_call_t *)sys_extpwritev }, /* 290 = extpwritev */
+ { AS(extpreadv_args), (sy_call_t *)sys_extpreadv }, /* 289 = extpreadv */
+ { AS(extpwritev_args), (sy_call_t *)sys_extpwritev }, /* 290 = extpwritev */
{ 0, (sy_call_t *)sys_nosys }, /* 291 = nosys */
{ 0, (sy_call_t *)sys_nosys }, /* 292 = nosys */
{ 0, (sy_call_t *)sys_nosys }, /* 293 = nosys */
{ AS(aio_write_args), (sy_call_t *)sys_aio_write }, /* 319 = aio_write */
{ AS(lio_listio_args), (sy_call_t *)sys_lio_listio }, /* 320 = lio_listio */
{ 0, (sy_call_t *)sys_yield }, /* 321 = yield */
- { AS(thr_sleep_args), (sy_call_t *)sys_thr_sleep }, /* 322 = thr_sleep */
- { AS(thr_wakeup_args), (sy_call_t *)sys_thr_wakeup }, /* 323 = thr_wakeup */
+ { 0, (sy_call_t *)sys_nosys }, /* 322 = thr_sleep */
+ { 0, (sy_call_t *)sys_nosys }, /* 323 = thr_wakeup */
{ AS(mlockall_args), (sy_call_t *)sys_mlockall }, /* 324 = mlockall */
{ 0, (sy_call_t *)sys_munlockall }, /* 325 = munlockall */
{ AS(__getcwd_args), (sy_call_t *)sys___getcwd }, /* 326 = __getcwd */
{ AS(kldsym_args), (sy_call_t *)sys_kldsym }, /* 337 = kldsym */
{ AS(jail_args), (sy_call_t *)sys_jail }, /* 338 = jail */
{ 0, (sy_call_t *)sys_nosys }, /* 339 = pioctl */
- { SYF_MPSAFE | AS(sigprocmask_args), (sy_call_t *)sys_sigprocmask }, /* 340 = sigprocmask */
+ { AS(sigprocmask_args), (sy_call_t *)sys_sigprocmask }, /* 340 = sigprocmask */
{ AS(sigsuspend_args), (sy_call_t *)sys_sigsuspend }, /* 341 = sigsuspend */
{ AS(sigaction_args), (sy_call_t *)sys_sigaction }, /* 342 = sigaction */
{ AS(sigpending_args), (sy_call_t *)sys_sigpending }, /* 343 = sigpending */
{ 0, (sy_call_t *)sys_nosys }, /* 447 = nosys */
{ 0, (sy_call_t *)sys_nosys }, /* 448 = nosys */
{ 0, (sy_call_t *)sys_nosys }, /* 449 = nosys */
- { SYF_MPSAFE | AS(varsym_set_args), (sy_call_t *)sys_varsym_set }, /* 450 = varsym_set */
- { SYF_MPSAFE | AS(varsym_get_args), (sy_call_t *)sys_varsym_get }, /* 451 = varsym_get */
- { SYF_MPSAFE | AS(varsym_list_args), (sy_call_t *)sys_varsym_list }, /* 452 = varsym_list */
+ { AS(varsym_set_args), (sy_call_t *)sys_varsym_set }, /* 450 = varsym_set */
+ { AS(varsym_get_args), (sy_call_t *)sys_varsym_get }, /* 451 = varsym_get */
+ { AS(varsym_list_args), (sy_call_t *)sys_varsym_list }, /* 452 = varsym_list */
{ AS(upc_register_args), (sy_call_t *)sys_upc_register }, /* 453 = upc_register */
{ AS(upc_control_args), (sy_call_t *)sys_upc_control }, /* 454 = upc_control */
{ AS(caps_sys_service_args), (sy_call_t *)sys_caps_sys_service }, /* 455 = caps_sys_service */
{ AS(umtx_sleep_args), (sy_call_t *)sys_umtx_sleep }, /* 469 = umtx_sleep */
{ AS(umtx_wakeup_args), (sy_call_t *)sys_umtx_wakeup }, /* 470 = umtx_wakeup */
{ AS(jail_attach_args), (sy_call_t *)sys_jail_attach }, /* 471 = jail_attach */
- { SYF_MPSAFE | AS(set_tls_area_args), (sy_call_t *)sys_set_tls_area }, /* 472 = set_tls_area */
- { SYF_MPSAFE | AS(get_tls_area_args), (sy_call_t *)sys_get_tls_area }, /* 473 = get_tls_area */
- { SYF_MPSAFE | AS(closefrom_args), (sy_call_t *)sys_closefrom }, /* 474 = closefrom */
+ { AS(set_tls_area_args), (sy_call_t *)sys_set_tls_area }, /* 472 = set_tls_area */
+ { AS(get_tls_area_args), (sy_call_t *)sys_get_tls_area }, /* 473 = get_tls_area */
+ { AS(closefrom_args), (sy_call_t *)sys_closefrom }, /* 474 = closefrom */
{ AS(stat_args), (sy_call_t *)sys_stat }, /* 475 = stat */
- { SYF_MPSAFE | AS(fstat_args), (sy_call_t *)sys_fstat }, /* 476 = fstat */
+ { AS(fstat_args), (sy_call_t *)sys_fstat }, /* 476 = fstat */
{ AS(lstat_args), (sy_call_t *)sys_lstat }, /* 477 = lstat */
{ AS(fhstat_args), (sy_call_t *)sys_fhstat }, /* 478 = fhstat */
{ AS(getdirentries_args), (sy_call_t *)sys_getdirentries }, /* 479 = getdirentries */
{ AS(fchownat_args), (sy_call_t *)sys_fchownat }, /* 507 = fchownat */
{ AS(unlinkat_args), (sy_call_t *)sys_unlinkat }, /* 508 = unlinkat */
{ AS(faccessat_args), (sy_call_t *)sys_faccessat }, /* 509 = faccessat */
- { SYF_MPSAFE | AS(mq_open_args), (sy_call_t *)sys_mq_open }, /* 510 = mq_open */
- { SYF_MPSAFE | AS(mq_close_args), (sy_call_t *)sys_mq_close }, /* 511 = mq_close */
- { SYF_MPSAFE | AS(mq_unlink_args), (sy_call_t *)sys_mq_unlink }, /* 512 = mq_unlink */
- { SYF_MPSAFE | AS(mq_getattr_args), (sy_call_t *)sys_mq_getattr }, /* 513 = mq_getattr */
- { SYF_MPSAFE | AS(mq_setattr_args), (sy_call_t *)sys_mq_setattr }, /* 514 = mq_setattr */
- { SYF_MPSAFE | AS(mq_notify_args), (sy_call_t *)sys_mq_notify }, /* 515 = mq_notify */
- { SYF_MPSAFE | AS(mq_send_args), (sy_call_t *)sys_mq_send }, /* 516 = mq_send */
- { SYF_MPSAFE | AS(mq_receive_args), (sy_call_t *)sys_mq_receive }, /* 517 = mq_receive */
- { SYF_MPSAFE | AS(mq_timedsend_args), (sy_call_t *)sys_mq_timedsend }, /* 518 = mq_timedsend */
- { SYF_MPSAFE | AS(mq_timedreceive_args), (sy_call_t *)sys_mq_timedreceive }, /* 519 = mq_timedreceive */
+ { AS(mq_open_args), (sy_call_t *)sys_mq_open }, /* 510 = mq_open */
+ { AS(mq_close_args), (sy_call_t *)sys_mq_close }, /* 511 = mq_close */
+ { AS(mq_unlink_args), (sy_call_t *)sys_mq_unlink }, /* 512 = mq_unlink */
+ { AS(mq_getattr_args), (sy_call_t *)sys_mq_getattr }, /* 513 = mq_getattr */
+ { AS(mq_setattr_args), (sy_call_t *)sys_mq_setattr }, /* 514 = mq_setattr */
+ { AS(mq_notify_args), (sy_call_t *)sys_mq_notify }, /* 515 = mq_notify */
+ { AS(mq_send_args), (sy_call_t *)sys_mq_send }, /* 516 = mq_send */
+ { AS(mq_receive_args), (sy_call_t *)sys_mq_receive }, /* 517 = mq_receive */
+ { AS(mq_timedsend_args), (sy_call_t *)sys_mq_timedsend }, /* 518 = mq_timedsend */
+ { AS(mq_timedreceive_args), (sy_call_t *)sys_mq_timedreceive }, /* 519 = mq_timedreceive */
};
* previous implementation done by Mark Tinguely.
*
* acct(char *path)
+ *
+ * MPALMOSTSAFE
*/
int
sys_acct(struct acct_args *uap)
if (error)
return (error);
+ get_mplock();
+
/*
* If accounting is to be started to a file, open that file for
* appending and make sure it's a 'normal'.
error = EACCES;
if (error) {
nlookup_done(&nd);
- return (error);
+ goto done;
}
vp = nd.nl_open_vp;
nd.nl_open_vp = NULL;
* don't try cleaning it up.
*/
if (uap->path == NULL)
- return (error);
+ goto done;
/*
* Save the new accounting file vnode, and schedule the new
*/
acctp = vp;
acctwatch(NULL);
+done:
+ rel_mplock();
return (error);
}
/*
* Given a file path, get an ACL for it
+ *
+ * MPALMOSTSAFE
*/
int
sys___acl_get_file(struct __acl_get_file_args *uap)
int error;
vp = NULL;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0)
error = nlookup(&nd);
error = vacl_get_acl(vp, uap->type, uap->aclp);
vrele(vp);
}
+ rel_mplock();
+
return (error);
}
/*
* Given a file path, set an ACL for it
+ *
+ * MPALMOSTSAFE
*/
int
sys___acl_set_file(struct __acl_set_file_args *uap)
int error;
vp = NULL;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0)
error = nlookup(&nd);
error = vacl_set_acl(vp, uap->type, uap->aclp);
vrele(vp);
}
+ rel_mplock();
+
return (error);
}
/*
* Given a file descriptor, get an ACL for it
+ *
+ * MPALMOSTSAFE
*/
int
sys___acl_get_fd(struct __acl_get_fd_args *uap)
KKASSERT(td->td_proc);
if ((error = holdvnode(td->td_proc->p_fd, uap->filedes, &fp)) != 0)
return(error);
+ get_mplock();
error = vacl_get_acl((struct vnode *)fp->f_data, uap->type, uap->aclp);
+ rel_mplock();
fdrop(fp);
+
return (error);
}
/*
* Given a file descriptor, set an ACL for it
+ *
+ * MPALMOSTSAFE
*/
int
sys___acl_set_fd(struct __acl_set_fd_args *uap)
KKASSERT(td->td_proc);
if ((error = holdvnode(td->td_proc->p_fd, uap->filedes, &fp)) != 0)
return(error);
+ get_mplock();
error = vacl_set_acl((struct vnode *)fp->f_data, uap->type, uap->aclp);
+ rel_mplock();
fdrop(fp);
return (error);
}
/*
* Given a file path, delete an ACL from it.
+ *
+ * MPALMOSTSAFE
*/
int
sys___acl_delete_file(struct __acl_delete_file_args *uap)
int error;
vp = NULL;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0)
error = nlookup(&nd);
error = vacl_delete(vp, uap->type);
vrele(vp);
}
+ rel_mplock();
+
return (error);
}
/*
* Given a file path, delete an ACL from it.
+ *
+ * MPALMOSTSAFE
*/
int
sys___acl_delete_fd(struct __acl_delete_fd_args *uap)
KKASSERT(td->td_proc);
if ((error = holdvnode(td->td_proc->p_fd, uap->filedes, &fp)) != 0)
return(error);
+ get_mplock();
error = vacl_delete((struct vnode *)fp->f_data, uap->type);
+ rel_mplock();
fdrop(fp);
return (error);
}
/*
* Given a file path, check an ACL for it
+ *
+ * MPALMOSTSAFE
*/
int
sys___acl_aclcheck_file(struct __acl_aclcheck_file_args *uap)
int error;
vp = NULL;
+ get_mplock();
error = nlookup_init(&nd, uap->path, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0)
error = nlookup(&nd);
error = vacl_aclcheck(vp, uap->type, uap->aclp);
vrele(vp);
}
+ rel_mplock();
return (error);
}
/*
* Given a file descriptor, check an ACL for it
+ *
+ * MPALMOSTSAFE
*/
int
sys___acl_aclcheck_fd(struct __acl_aclcheck_fd_args *uap)
KKASSERT(td->td_proc);
if ((error = holdvnode(td->td_proc->p_fd, uap->filedes, &fp)) != 0)
return(error);
+ get_mplock();
error = vacl_aclcheck((struct vnode *)fp->f_data, uap->type, uap->aclp);
+ rel_mplock();
fdrop(fp);
return (error);
}
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sys_checkpoint(struct sys_checkpoint_args *uap)
{
if (uap->pid != -1 && uap->pid != p->p_pid)
return (EINVAL);
+ get_mplock();
+
switch (uap->type) {
case CKPT_FREEZE:
fp = NULL;
fdrop(fp);
break;
case CKPT_THAW:
- if (uap->pid != -1)
- return EINVAL;
- if ((fp = holdfp(p->p_fd, uap->fd, FREAD)) == NULL)
- return EBADF;
+ if (uap->pid != -1) {
+ error = EINVAL;
+ break;
+ }
+ if ((fp = holdfp(p->p_fd, uap->fd, FREAD)) == NULL) {
+ error = EBADF;
+ break;
+ }
uap->sysmsg_result = uap->retval;
error = ckpt_thaw_proc(lp, fp);
fdrop(fp);
error = EOPNOTSUPP;
break;
}
+ rel_mplock();
return error;
}
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_shutdown(struct shutdown_args *uap)
{
int error;
+ get_mplock();
error = kern_shutdown(uap->s, uap->how);
+ rel_mplock();
return (error);
}
/*
* Return pathconf information about a file descriptor.
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_fpathconf(struct fpathconf_args *uap)
{
struct vnode *vp;
int error = 0;
- KKASSERT(p);
-
if ((fp = holdfp(p->p_fd, uap->fd, -1)) == NULL)
return (EBADF);
case DTYPE_FIFO:
case DTYPE_VNODE:
vp = (struct vnode *)fp->f_data;
+ get_mplock();
error = VOP_PATHCONF(vp, uap->name, &uap->sysmsg_reg);
+ rel_mplock();
break;
default:
error = EOPNOTSUPP;
*
* Just attempt to get a record lock of the requested type on
* the entire file (l_whence = SEEK_SET, l_start = 0, l_len = 0).
+ *
+ * MPALMOSTSAFE
*/
int
sys_flock(struct flock_args *uap)
if ((fp = holdfp(p->p_fd, uap->fd, -1)) == NULL)
return (EBADF);
+ get_mplock();
if (fp->f_type != DTYPE_VNODE) {
error = EOPNOTSUPP;
goto done;
else
error = VOP_ADVLOCK(vp, (caddr_t)fp, F_SETLK, &lf, F_WAIT);
done:
+ rel_mplock();
fdrop(fp);
return (error);
}
* consists of only the ``open()'' routine, because all subsequent
* references to this file will be direct to the other driver.
*/
-/* ARGSUSED */
static int
fdopen(struct dev_open_args *ap)
{
return (kn->kn_data != 0);
}
+/*
+ * MPSAFE
+ */
int
sys_kqueue(struct kqueue_args *uap)
{
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_kevent(struct kevent_args *uap)
{
struct timespec ts;
int i, n, nerrors, error;
- KKASSERT(p);
-
fp = holdfp(p->p_fd, uap->fd, -1);
if (fp == NULL)
return (EBADF);
kq = (struct kqueue *)fp->f_data;
nerrors = 0;
+ get_mplock();
while (uap->nchanges > 0) {
n = uap->nchanges > KQ_NEVENTS ? KQ_NEVENTS : uap->nchanges;
error = copyin(uap->changelist, kq->kq_kev,
- n * sizeof(struct kevent));
+ n * sizeof(struct kevent));
if (error)
goto done;
for (i = 0; i < n; i++) {
goto done;
}
- error = kqueue_scan(fp, uap->nevents, uap->eventlist, uap->timeout, td, &uap->sysmsg_result);
+ error = kqueue_scan(fp, uap->nevents, uap->eventlist,
+ uap->timeout, td, &uap->sysmsg_result);
done:
+ rel_mplock();
if (fp != NULL)
fdrop(fp);
return (error);
/*
* execve() system call.
+ *
+ * MPALMOSTSAFE
*/
int
sys_execve(struct execve_args *uap)
struct image_args args;
int error;
- error = nlookup_init(&nd, uap->fname, UIO_USERSPACE, NLC_FOLLOW);
bzero(&args, sizeof(args));
+
+ get_mplock();
+ error = nlookup_init(&nd, uap->fname, UIO_USERSPACE, NLC_FOLLOW);
if (error == 0) {
error = exec_copyin_args(&args, uap->fname, PATH_USERSPACE,
uap->argv, uap->envv);
exit1(W_EXITCODE(0, SIGABRT));
/* NOTREACHED */
}
+ rel_mplock();
/*
* The syscall result is returned in registers to the new program.
* Death of process.
*
* SYS_EXIT_ARGS(int rval)
+ *
+ * MPALMOSTSAFE
*/
int
sys_exit(struct exit_args *uap)
{
+ get_mplock();
exit1(W_EXITCODE(uap->rval, 0));
/* NOTREACHED */
+ rel_mplock();
}
/*
* Extended exit --
* Death of a lwp or process with optional bells and whistles.
+ *
+ * MPALMOSTSAFE
*/
int
sys_extexit(struct extexit_args *uap)
case EXTEXIT_PROC:
case EXTEXIT_LWP:
break;
-
default:
return (EINVAL);
}
switch (action) {
case EXTEXIT_SIMPLE:
break;
-
case EXTEXIT_SETINT:
error = copyout(&uap->status, uap->addr, sizeof(uap->status));
if (error)
return (error);
break;
-
default:
return (EINVAL);
}
+ get_mplock();
+
switch (who) {
case EXTEXIT_LWP:
/*
}
/* else last lwp in proc: do the real thing */
/* FALLTHROUGH */
-
default: /* to help gcc */
case EXTEXIT_PROC:
exit1(W_EXITCODE(uap->status, 0));
}
/* NOTREACHED */
+ rel_mplock(); /* safety */
}
/*
kfree(lp, M_LWP);
}
+/*
+ * MPSAFE
+ */
int
sys_wait4(struct wait_args *uap)
{
struct rusage rusage;
int error, status;
- error = kern_wait(uap->pid, uap->status ? &status : NULL,
- uap->options, uap->rusage ? &rusage : NULL, &uap->sysmsg_result);
+ error = kern_wait(uap->pid, (uap->status ? &status : NULL),
+ uap->options, (uap->rusage ? &rusage : NULL),
+ &uap->sysmsg_result);
if (error == 0 && uap->status)
error = copyout(&status, uap->status, sizeof(*uap->status));
* wait1()
*
* wait_args(int pid, int *status, int options, struct rusage *rusage)
+ *
+ * MPALMOSTSAFE
*/
int
kern_wait(pid_t pid, int *status, int options, struct rusage *rusage, int *res)
pid = -q->p_pgid;
if (options &~ (WUNTRACED|WNOHANG|WCONTINUED|WLINUXCLONE))
return (EINVAL);
+ get_mplock();
loop:
/*
* Hack for backwards compatibility with badly written user code.
proc_reparent(p, t);
ksignal(t, SIGCHLD);
wakeup((caddr_t)t);
- return (0);
+ error = 0;
+ goto done;
}
/*
vm_waitproc(p);
kfree(p, M_PROC);
nprocs--;
- return (0);
+ error = 0;
+ goto done;
}
if (p->p_stat == SSTOP && (p->p_flag & P_WAITED) == 0 &&
(p->p_flag & P_TRACED || options & WUNTRACED)) {
/* Zero rusage so we get something consistent. */
if (rusage)
bzero(rusage, sizeof(rusage));
- return (0);
+ error = 0;
+ goto done;
}
if (options & WCONTINUED && (p->p_flag & P_CONTINUED)) {
*res = p->p_pid;
if (status)
*status = SIGCONT;
- return (0);
+ error = 0;
+ goto done;
}
}
- if (nfound == 0)
- return (ECHILD);
+ if (nfound == 0) {
+ error = ECHILD;
+ goto done;
+ }
if (options & WNOHANG) {
*res = 0;
- return (0);
+ error = 0;
+ goto done;
}
error = tsleep((caddr_t)q, PCATCH, "wait", 0);
- if (error)
+ if (error) {
+done:
+ rel_mplock();
return (error);
+ }
goto loop;
}
RB_GENERATE2(lwp_rb_tree, lwp, u.lwp_rbnode, rb_lwp_compare, lwpid_t, lwp_tid);
-
-/* ARGSUSED */
+/*
+ * Fork system call
+ *
+ * MPALMOSTSAFE
+ */
int
sys_fork(struct fork_args *uap)
{
struct proc *p2;
int error;
+ get_mplock();
error = fork1(lp, RFFDG | RFPROC | RFPGLOCK, &p2);
if (error == 0) {
start_forked_proc(lp, p2);
uap->sysmsg_fds[0] = p2->p_pid;
uap->sysmsg_fds[1] = 0;
}
+ rel_mplock();
return error;
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_vfork(struct vfork_args *uap)
{
struct proc *p2;
int error;
+ get_mplock();
error = fork1(lp, RFFDG | RFPROC | RFPPWAIT | RFMEM | RFPGLOCK, &p2);
if (error == 0) {
start_forked_proc(lp, p2);
uap->sysmsg_fds[0] = p2->p_pid;
uap->sysmsg_fds[1] = 0;
}
+ rel_mplock();
return error;
}
* created.
*
* rfork { int flags }
+ *
+ * MPALMOSTSAFE
*/
int
sys_rfork(struct rfork_args *uap)
if ((uap->flags & RFKERNELONLY) != 0)
return (EINVAL);
+ get_mplock();
error = fork1(lp, uap->flags | RFPGLOCK, &p2);
if (error == 0) {
if (p2)
uap->sysmsg_fds[0] = p2 ? p2->p_pid : 0;
uap->sysmsg_fds[1] = 0;
}
+ rel_mplock();
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_lwp_create(struct lwp_create_args *uap)
{
if (error)
goto fail2;
+ get_mplock();
plimit_lwp_fork(p); /* force exclusive access */
lp = lwp_fork(curthread->td_lwp, p, RFPROC);
error = cpu_prepare_lwp(lp, ¶ms);
lp->lwp_stat = LSRUN;
p->p_usched->setrunqueue(lp);
crit_exit();
+ rel_mplock();
return (0);
lp->lwp_thread->td_flags |= TDF_EXITING;
PHOLD(p);
lwp_dispose(lp);
+ rel_mplock();
fail2:
return (error);
}
* jail()
*
* jail_args(syscallarg(struct jail *) jail)
+ *
+ * MPALMOSTSAFE
*/
int
sys_jail(struct jail_args *uap)
pr = kmalloc(sizeof(*pr), M_PRISON, M_WAITOK | M_ZERO);
SLIST_INIT(&pr->pr_ips);
+ get_mplock();
switch (jversion) {
case 0:
goto out;
uap->sysmsg_result = pr->pr_id;
+ rel_mplock();
return (0);
out:
SLIST_REMOVE_HEAD(&pr->pr_ips, entries);
kfree(jip, M_PRISON);
}
+ rel_mplock();
kfree(pr, M_PRISON);
return (error);
}
/*
* int jail_attach(int jid);
+ *
+ * MPALMOSTSAFE
*/
int
sys_jail_attach(struct jail_attach_args *uap)
error = priv_check(td, PRIV_JAIL_ATTACH);
if (error)
return(error);
-
- return(kern_jail_attach(uap->jid));
+ get_mplock();
+ error = kern_jail_attach(uap->jid);
+ rel_mplock();
+ return (error);
}
static void
static int ktrsetchildren (struct proc *,struct proc *,int,int, ktrace_node_t);
static int ktrops (struct proc *,struct proc *,int,int, ktrace_node_t);
+/*
+ * MPSAFE
+ */
static struct ktr_header *
ktrgetheader(int type)
{
#endif
+/*
+ * MPALMOSTSAFE
+ */
int
sys_ktrace(struct ktrace_args *uap)
{
struct nlookupdata nd;
ktrace_node_t tracenode = NULL;
+ get_mplock();
curp->p_traceflag |= KTRFAC_ACTIVE;
if (ops != KTROP_CLEAR) {
/*
if (error) {
curp->p_traceflag &= ~KTRFAC_ACTIVE;
nlookup_done(&nd);
- return (error);
+ goto done;
}
MALLOC(tracenode, ktrace_node_t, sizeof (struct ktrace_node),
M_KTRACE, M_WAITOK | M_ZERO);
if (tracenode)
ktrdestroy(&tracenode);
curp->p_traceflag &= ~KTRFAC_ACTIVE;
+ rel_mplock();
return (error);
#else
return ENOSYS;
/*
* utrace system call
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_utrace(struct utrace_args *uap)
{
if (!copyin(uap->addr, cp, uap->len)) {
kth->ktr_buf = cp;
kth->ktr_len = uap->len;
+ get_mplock();
ktrwrite(p, kth, NULL);
+ rel_mplock();
}
FREE(kth, M_KTRACE);
FREE(cp, M_KTRACE);
/*
* Syscalls.
+ *
+ * MPALMOSTSAFE
*/
-
int
sys_kldload(struct kldload_args *uap)
{
modname = file;
}
- if ((error = linker_load_module(kldname, modname, NULL, NULL, &lf)) != 0)
+ get_mplock();
+ error = linker_load_module(kldname, modname, NULL, NULL, &lf);
+ rel_mplock();
+ if (error)
goto out;
lf->userrefs++;
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_kldunload(struct kldunload_args *uap)
{
if ((error = priv_check(td, PRIV_KLD_UNLOAD)) != 0)
return error;
+ get_mplock();
lf = linker_find_file_by_id(uap->fileid);
if (lf) {
KLD_DPF(FILE, ("kldunload: lf->userrefs=%d\n", lf->userrefs));
error = linker_file_unload(lf);
if (error)
lf->userrefs++;
- } else
+ } else {
error = ENOENT;
-
+ }
out:
+ rel_mplock();
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_kldfind(struct kldfind_args *uap)
{
char *filename = NULL, *modulename;
linker_file_t lf;
- int error = 0;
+ int error;
uap->sysmsg_result = -1;
if (modulename == NULL)
modulename = filename;
+ get_mplock();
lf = linker_find_file_by_name(modulename);
if (lf)
uap->sysmsg_result = lf->id;
else
error = ENOENT;
+ rel_mplock();
out:
if (filename)
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_kldnext(struct kldnext_args *uap)
{
linker_file_t lf;
int error = 0;
- if (uap->fileid == 0)
+ get_mplock();
+ if (uap->fileid == 0) {
lf = TAILQ_FIRST(&linker_files);
- else {
+ } else {
lf = linker_find_file_by_id(uap->fileid);
if (lf == NULL) {
error = ENOENT;
uap->sysmsg_result = 0;
out:
+ rel_mplock();
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_kldstat(struct kldstat_args *uap)
{
struct kld_file_stat* stat;
int namelen;
+ get_mplock();
lf = linker_find_file_by_id(uap->fileid);
if (!lf) {
error = ENOENT;
uap->sysmsg_result = 0;
out:
+ rel_mplock();
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_kldfirstmod(struct kldfirstmod_args *uap)
{
linker_file_t lf;
int error = 0;
+ get_mplock();
lf = linker_find_file_by_id(uap->fileid);
if (lf) {
if (TAILQ_FIRST(&lf->modules))
uap->sysmsg_result = module_getid(TAILQ_FIRST(&lf->modules));
else
uap->sysmsg_result = 0;
- } else
+ } else {
error = ENOENT;
+ }
+ rel_mplock();
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_kldsym(struct kldsym_args *uap)
{
struct kld_sym_lookup lookup;
int error = 0;
+ get_mplock();
if ((error = copyin(uap->data, &lookup, sizeof(lookup))) != 0)
goto out;
if (lookup.version != sizeof(lookup) || uap->cmd != KLDSYM_LOOKUP) {
error = ENOENT;
}
out:
+ rel_mplock();
if (symstr)
kfree(symstr, M_TEMP);
return error;
/*
* Syscalls.
+ *
+ * MPALMOSTSAFE
*/
int
sys_modnext(struct modnext_args *uap)
{
module_t mod;
+ int error;
+ get_mplock();
uap->sysmsg_result = -1;
if (uap->modid == 0) {
mod = TAILQ_FIRST(&modules);
if (mod) {
uap->sysmsg_result = mod->id;
- return 0;
- } else
- return ENOENT;
+ error = 0;
+ goto done;
+ } else {
+ error = ENOENT;
+ goto done;
+ }
}
mod = module_lookupbyid(uap->modid);
- if (!mod)
- return ENOENT;
+ if (!mod) {
+ error = ENOENT;
+ goto done;
+ }
if (TAILQ_NEXT(mod, link))
uap->sysmsg_result = TAILQ_NEXT(mod, link)->id;
else
uap->sysmsg_result = 0;
- return 0;
+ error = 0;
+done:
+ rel_mplock();
+ return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_modfnext(struct modfnext_args *uap)
{
module_t mod;
+ int error;
+ get_mplock();
uap->sysmsg_result = -1;
mod = module_lookupbyid(uap->modid);
- if (!mod)
- return ENOENT;
+ if (!mod) {
+ error = ENOENT;
+ goto done;
+ }
if (TAILQ_NEXT(mod, flink))
uap->sysmsg_result = TAILQ_NEXT(mod, flink)->id;
else
uap->sysmsg_result = 0;
- return 0;
+ error = 0;
+done:
+ rel_mplock();
+ return error;
}
struct module_stat_v1 {
int id;
};
+/*
+ * MPALMOSTSAFE
+ */
int
sys_modstat(struct modstat_args *uap)
{
module_t mod;
- int error = 0;
+ int error;
int namelen;
int version;
struct module_stat* stat;
+ get_mplock();
mod = module_lookupbyid(uap->modid);
- if (!mod)
- return ENOENT;
+ if (!mod) {
+ error = ENOENT;
+ goto out;
+ }
stat = uap->stat;
uap->sysmsg_result = 0;
out:
+ rel_mplock();
return error;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_modfind(struct modfind_args *uap)
{
- int error = 0;
+ int error;
char name[MAXMODNAME];
module_t mod;
+ get_mplock();
if ((error = copyinstr(uap->name, name, sizeof name, 0)) != 0)
goto out;
uap->sysmsg_result = mod->id;
out:
+ rel_mplock();
return error;
}
* See the timex.h header file for synopsis and API description. Note
* that the timex.constant structure member has a dual purpose to set
* the time constant and to set the TAI offset.
+ *
+ * MPALMOSTSAFE
*/
int
sys_ntp_adjtime(struct ntp_adjtime_args *uap)
error = priv_check(td, PRIV_NTP_ADJTIME);
if (error)
return (error);
+
+ get_mplock();
crit_enter();
if (modes & MOD_MAXERROR)
time_maxerror = ntv.maxerror;
ntv.stbcnt = pps_stbcnt;
#endif /* PPS_SYNC */
crit_exit();
+ rel_mplock();
error = copyout((caddr_t)&ntv, (caddr_t)uap->tp, sizeof(ntv));
if (error)
return ret;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sched_setparam(struct sched_setparam_args *uap)
{
struct proc *p = curproc;
struct lwp *lp;
int e;
-
struct sched_param sched_param;
+
copyin(uap->param, &sched_param, sizeof(sched_param));
+ get_mplock();
if ((e = p31b_proc(p, uap->pid, &p)) == 0) {
lp = FIRST_LWP_IN_PROC(p); /* XXX lwp */
e = ksched_setparam(&uap->sysmsg_reg, ksched, lp,
- (const struct sched_param *)&sched_param);
+ (const struct sched_param *)&sched_param);
}
+ rel_mplock();
return e;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sched_getparam(struct sched_getparam_args *uap)
{
struct sched_param sched_param;
int e;
+ get_mplock();
if (uap->pid != 0 && uap->pid != p->p_pid) {
e = p31b_proc(p, uap->pid, &targetp);
if (e)
- return e;
+ goto done;
} else {
targetp = p;
}
lp = FIRST_LWP_IN_PROC(targetp); /* XXX lwp */
e = ksched_getparam(&uap->sysmsg_reg, ksched, lp, &sched_param);
-
- if (!e)
+done:
+ rel_mplock();
+ if (e == 0)
copyout(&sched_param, uap->param, sizeof(sched_param));
-
return e;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sched_setscheduler(struct sched_setscheduler_args *uap)
{
struct proc *p = curproc;
struct lwp *lp;
int e;
-
struct sched_param sched_param;
+
copyin(uap->param, &sched_param, sizeof(sched_param));
+ get_mplock();
if ((e = p31b_proc(p, uap->pid, &p)) == 0) {
lp = FIRST_LWP_IN_PROC(p); /* XXX lwp */
e = ksched_setscheduler(&uap->sysmsg_reg, ksched, lp,
- uap->policy, (const struct sched_param *)&sched_param);
+ uap->policy,
+ (const struct sched_param *)&sched_param);
}
+ rel_mplock();
return e;
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sched_getscheduler(struct sched_getscheduler_args *uap)
{
struct lwp *lp;
int e;
+ get_mplock();
if (uap->pid != 0 && uap->pid != p->p_pid) {
e = p31b_proc(p, uap->pid, &targetp);
if (e)
- return e;
+ goto done;
} else {
targetp = p;
}
lp = FIRST_LWP_IN_PROC(targetp); /* XXX lwp */
e = ksched_getscheduler(&uap->sysmsg_reg, ksched, lp);
-
+done:
+ rel_mplock();
return e;
}
+/*
+ * MPSAFE
+ */
int
sys_sched_yield(struct sched_yield_args *uap)
{
return ksched_yield(&uap->sysmsg_reg, ksched);
}
+/*
+ * MPSAFE
+ */
int
sys_sched_get_priority_max(struct sched_get_priority_max_args *uap)
{
return ksched_get_priority_max(&uap->sysmsg_reg, ksched, uap->policy);
}
+/*
+ * MPSAFE
+ */
int
sys_sched_get_priority_min(struct sched_get_priority_min_args *uap)
{
return ksched_get_priority_min(&uap->sysmsg_reg, ksched, uap->policy);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sched_rr_get_interval(struct sched_rr_get_interval_args *uap)
{
struct proc *p = curproc;
struct lwp *lp = curthread->td_lwp;
+ get_mplock();
if ((e = p31b_proc(p, uap->pid, &p)) == 0) {
- e = ksched_rr_get_interval(&uap->sysmsg_reg, ksched,
- lp, uap->interval);
+ e = ksched_rr_get_interval(&uap->sysmsg_reg, ksched,
+ lp, uap->interval);
}
+ rel_mplock();
return e;
}
#endif
-static void p31binit(void *notused)
+static void
+p31binit(void *notused)
{
(void) sched_attach();
p31b_setcfg(CTL_P1003_1B_PAGESIZE, PAGE_SIZE);
static MALLOC_DEFINE(M_CRED, "cred", "credentials");
/*
- * NOT MP SAFE due to p_pptr access
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_getpid(struct getpid_args *uap)
{
uap->sysmsg_fds[0] = p->p_pid;
#if defined(COMPAT_43) || defined(COMPAT_SUNOS)
+ get_mplock();
uap->sysmsg_fds[1] = p->p_pptr->p_pid;
+ rel_mplock();
#endif
return (0);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_getppid(struct getppid_args *uap)
{
struct proc *p = curproc;
+ get_mplock();
uap->sysmsg_result = p->p_pptr->p_pid;
+ rel_mplock();
+
return (0);
}
-/* ARGSUSED */
+/*
+ * MPSAFE
+ */
int
sys_lwp_gettid(struct lwp_gettid_args *uap)
{
/*
* Get process group ID; note that POSIX getpgrp takes no parameter
*
- * MP SAFE
+ * MPSAFE XXX pgrp
*/
int
sys_getpgrp(struct getpgrp_args *uap)
/*
* Get an arbitrary pid's process group id
+ *
+ * MPALMOSTSAFE
*/
int
sys_getpgid(struct getpgid_args *uap)
{
struct proc *p = curproc;
struct proc *pt;
+ int error;
- pt = p;
- if (uap->pid == 0)
- goto found;
+ get_mplock();
+ error = 0;
- if ((pt = pfind(uap->pid)) == 0)
- return ESRCH;
-found:
- uap->sysmsg_result = pt->p_pgrp->pg_id;
- return 0;
+ if (uap->pid == 0) {
+ pt = p;
+ } else {
+ pt = pfind(uap->pid);
+ if (pt == NULL)
+ error = ESRCH;
+ }
+ if (error == 0)
+ uap->sysmsg_result = pt->p_pgrp->pg_id;
+ rel_mplock();
+ return (error);
}
/*
* Get an arbitrary pid's session id.
+ *
+ * MPALMOSTSAFE
*/
int
sys_getsid(struct getsid_args *uap)
{
struct proc *p = curproc;
struct proc *pt;
+ int error;
- pt = p;
- if (uap->pid == 0)
- goto found;
+ get_mplock();
+ error = 0;
- if ((pt = pfind(uap->pid)) == 0)
- return ESRCH;
-found:
- uap->sysmsg_result = pt->p_session->s_sid;
- return 0;
+ if (uap->pid == 0) {
+ pt = p;
+ } else {
+ pt = pfind(uap->pid);
+ if (pt == NULL)
+ error = ESRCH;
+ }
+ if (error == 0)
+ uap->sysmsg_result = pt->p_session->s_sid;
+ rel_mplock();
+ return (error);
}
/*
- * getuid() - MP SAFE
+ * getuid()
+ *
+ * MPSAFE XXX ucred
*/
-/* ARGSUSED */
int
sys_getuid(struct getuid_args *uap)
{
}
/*
- * geteuid() - MP SAFE
+ * geteuid()
+ *
+ * MPSAFE XXX ucred
*/
-/* ARGSUSED */
int
sys_geteuid(struct geteuid_args *uap)
{
}
/*
- * getgid() - MP SAFE
+ * getgid()
+ *
+ * MPSAFE XXX UCRED
*/
-/* ARGSUSED */
int
sys_getgid(struct getgid_args *uap)
{
* via getgroups. This syscall exists because it is somewhat painful to do
* correctly in a library function.
*
- * MP SAFE
+ * MPSAFE
*/
-/* ARGSUSED */
int
sys_getegid(struct getegid_args *uap)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_getgroups(struct getgroups_args *uap)
{
u_int ngrp;
int error;
- if (p == NULL) /* API enforcement */
- return(EPERM);
cr = p->p_ucred;
-
if ((ngrp = uap->gidsetsize) == 0) {
uap->sysmsg_result = cr->cr_ngroups;
return (0);
if (ngrp < cr->cr_ngroups)
return (EINVAL);
ngrp = cr->cr_ngroups;
- if ((error = copyout((caddr_t)cr->cr_groups,
- (caddr_t)uap->gidset, ngrp * sizeof(gid_t))))
- return (error);
- uap->sysmsg_result = ngrp;
- return (0);
+ error = copyout((caddr_t)cr->cr_groups,
+ (caddr_t)uap->gidset, ngrp * sizeof(gid_t));
+ if (error == 0)
+ uap->sysmsg_result = ngrp;
+ return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setsid(struct setsid_args *uap)
{
struct proc *p = curproc;
+ int error;
+ get_mplock();
if (p->p_pgid == p->p_pid || pgfind(p->p_pid)) {
- return (EPERM);
+ error = EPERM;
} else {
- (void)enterpgrp(p, p->p_pid, 1);
+ enterpgrp(p, p->p_pid, 1);
uap->sysmsg_result = p->p_pid;
- return (0);
+ error = 0;
}
+ rel_mplock();
+ return (error);
}
/*
* if pgid != pid
* there must exist some pid in same session having pgid (EPERM)
* pid must not be session leader (EPERM)
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_setpgid(struct setpgid_args *uap)
{
struct proc *curp = curproc;
struct proc *targp; /* target process */
struct pgrp *pgrp; /* target pgrp */
+ int error;
if (uap->pgid < 0)
return (EINVAL);
+
+ get_mplock();
if (uap->pid != 0 && uap->pid != curp->p_pid) {
- if ((targp = pfind(uap->pid)) == 0 || !inferior(targp))
- return (ESRCH);
- if (targp->p_pgrp == NULL || targp->p_session != curp->p_session)
- return (EPERM);
- if (targp->p_flag & P_EXEC)
- return (EACCES);
- } else
+ if ((targp = pfind(uap->pid)) == 0 || !inferior(targp)) {
+ error = ESRCH;
+ goto done;
+ }
+ if (targp->p_pgrp == NULL ||
+ targp->p_session != curp->p_session) {
+ error = EPERM;
+ goto done;
+ }
+ if (targp->p_flag & P_EXEC) {
+ error = EACCES;
+ goto done;
+ }
+ } else {
targp = curp;
- if (SESS_LEADER(targp))
- return (EPERM);
- if (uap->pgid == 0)
+ }
+ if (SESS_LEADER(targp)) {
+ error = EPERM;
+ goto done;
+ }
+ 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)
- return (EPERM);
- return (enterpgrp(targp, uap->pgid, 0));
+ pgrp->pg_session != curp->p_session) {
+ error = EPERM;
+ goto done;
+ }
+ }
+ error = enterpgrp(targp, uap->pgid, 0);
+done:
+ rel_mplock();
+ return (error);
}
/*
*/
#define POSIX_APPENDIX_B_4_2_2
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setuid(struct setuid_args *uap)
{
uid_t uid;
int error;
- if (p == NULL) /* API enforcement */
- return(EPERM);
+ get_mplock();
cr = p->p_ucred;
/*
uid != cr->cr_uid && /* allow setuid(geteuid()) */
#endif
(error = priv_check_cred(cr, PRIV_CRED_SETUID, 0)))
- return (error);
+ goto done;
#ifdef _POSIX_SAVED_IDS
/*
change_euid(uid);
setsugid();
}
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_seteuid(struct seteuid_args *uap)
{
uid_t euid;
int error;
- if (p == NULL) /* API enforcement */
- return(EPERM);
-
cr = p->p_ucred;
euid = uap->euid;
if (euid != cr->cr_ruid && /* allow seteuid(getuid()) */
euid != cr->cr_svuid && /* allow seteuid(saved uid) */
- (error = priv_check_cred(cr, PRIV_CRED_SETEUID, 0)))
+ (error = priv_check_cred(cr, PRIV_CRED_SETEUID, 0))) {
return (error);
+ }
+
/*
* Everything's okay, do it. Copy credentials so other references do
* not see our changes.
*/
if (cr->cr_uid != euid) {
+ get_mplock();
change_euid(euid);
setsugid();
+ rel_mplock();
}
return (0);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setgid(struct setgid_args *uap)
{
gid_t gid;
int error;
- if (p == NULL) /* API enforcement */
- return(EPERM);
+ get_mplock();
cr = p->p_ucred;
/*
#ifdef POSIX_APPENDIX_B_4_2_2 /* Use BSD-compat clause from B.4.2.2 */
gid != cr->cr_groups[0] && /* allow setgid(getegid()) */
#endif
- (error = priv_check_cred(cr, PRIV_CRED_SETGID, 0)))
- return (error);
+ (error = priv_check_cred(cr, PRIV_CRED_SETGID, 0))) {
+ goto done;
+ }
#ifdef _POSIX_SAVED_IDS
/*
cr->cr_groups[0] = gid;
setsugid();
}
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setegid(struct setegid_args *uap)
{
gid_t egid;
int error;
- if (p == NULL) /* API enforcement */
- return(EPERM);
+ get_mplock();
cr = p->p_ucred;
-
egid = uap->egid;
if (egid != cr->cr_rgid && /* allow setegid(getgid()) */
egid != cr->cr_svgid && /* allow setegid(saved gid) */
- (error = priv_check_cred(cr, PRIV_CRED_SETEGID, 0)))
- return (error);
+ (error = priv_check_cred(cr, PRIV_CRED_SETEGID, 0))) {
+ goto done;
+ }
if (cr->cr_groups[0] != egid) {
cr = cratom(&p->p_ucred);
cr->cr_groups[0] = egid;
setsugid();
}
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setgroups(struct setgroups_args *uap)
{
u_int ngrp;
int error;
- if (p == NULL) /* API enforcement */
- return(EPERM);
+ get_mplock();
cr = p->p_ucred;
if ((error = priv_check_cred(cr, PRIV_CRED_SETGROUPS, 0)))
- return (error);
+ goto done;
ngrp = uap->gidsetsize;
- if (ngrp > NGROUPS)
- return (EINVAL);
+ if (ngrp > NGROUPS) {
+ error = EINVAL;
+ goto done;
+ }
/*
* XXX A little bit lazy here. We could test if anything has
* changed before cratom() and setting P_SUGID.
*/
cr->cr_ngroups = 1;
} else {
- if ((error = copyin((caddr_t)uap->gidset,
- (caddr_t)cr->cr_groups, ngrp * sizeof(gid_t))))
- return (error);
+ error = copyin(uap->gidset, cr->cr_groups,
+ ngrp * sizeof(gid_t));
+ if (error)
+ goto done;
cr->cr_ngroups = ngrp;
}
setsugid();
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setreuid(struct setreuid_args *uap)
{
uid_t ruid, euid;
int error;
- if (p == NULL) /* API enforcement */
- return(EPERM);
+ get_mplock();
cr = p->p_ucred;
ruid = uap->ruid;
if (((ruid != (uid_t)-1 && ruid != cr->cr_ruid && ruid != cr->cr_svuid) ||
(euid != (uid_t)-1 && euid != cr->cr_uid &&
euid != cr->cr_ruid && euid != cr->cr_svuid)) &&
- (error = priv_check_cred(cr, PRIV_CRED_SETREUID, 0)) != 0)
- return (error);
+ (error = priv_check_cred(cr, PRIV_CRED_SETREUID, 0)) != 0) {
+ goto done;
+ }
if (euid != (uid_t)-1 && cr->cr_uid != euid) {
cr = change_euid(euid);
cr->cr_svuid = cr->cr_uid;
setsugid();
}
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setregid(struct setregid_args *uap)
{
gid_t rgid, egid;
int error;
- if (p == NULL) /* API enforcement */
- return(EPERM);
+ get_mplock();
cr = p->p_ucred;
rgid = uap->rgid;
if (((rgid != (gid_t)-1 && rgid != cr->cr_rgid && rgid != cr->cr_svgid) ||
(egid != (gid_t)-1 && egid != cr->cr_groups[0] &&
egid != cr->cr_rgid && egid != cr->cr_svgid)) &&
- (error = priv_check_cred(cr, PRIV_CRED_SETREGID, 0)) != 0)
- return (error);
+ (error = priv_check_cred(cr, PRIV_CRED_SETREGID, 0)) != 0) {
+ goto done;
+ }
if (egid != (gid_t)-1 && cr->cr_groups[0] != egid) {
cr = cratom(&p->p_ucred);
cr->cr_svgid = cr->cr_groups[0];
setsugid();
}
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
/*
* setresuid(ruid, euid, suid) is like setreuid except control over the
* saved uid is explicit.
+ *
+ * MPALMOSTSAFE
*/
-
-/* ARGSUSED */
int
sys_setresuid(struct setresuid_args *uap)
{
uid_t ruid, euid, suid;
int error;
+ get_mplock();
cr = p->p_ucred;
+
ruid = uap->ruid;
euid = uap->euid;
suid = uap->suid;
euid != cr->cr_uid) ||
(suid != (uid_t)-1 && suid != cr->cr_ruid && suid != cr->cr_svuid &&
suid != cr->cr_uid)) &&
- (error = priv_check_cred(cr, PRIV_CRED_SETRESUID, 0)) != 0)
- return (error);
+ (error = priv_check_cred(cr, PRIV_CRED_SETRESUID, 0)) != 0) {
+ goto done;
+ }
if (euid != (uid_t)-1 && cr->cr_uid != euid) {
cr = change_euid(euid);
setsugid();
cr->cr_svuid = suid;
setsugid();
}
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
/*
* setresgid(rgid, egid, sgid) is like setregid except control over the
* saved gid is explicit.
+ *
+ * MPALMOSTSAFE
*/
-
-/* ARGSUSED */
int
sys_setresgid(struct setresgid_args *uap)
{
gid_t rgid, egid, sgid;
int error;
+ get_mplock();
cr = p->p_ucred;
rgid = uap->rgid;
egid = uap->egid;
egid != cr->cr_groups[0]) ||
(sgid != (gid_t)-1 && sgid != cr->cr_rgid && sgid != cr->cr_svgid &&
sgid != cr->cr_groups[0])) &&
- (error = priv_check_cred(cr, PRIV_CRED_SETRESGID, 0)) != 0)
- return (error);
+ (error = priv_check_cred(cr, PRIV_CRED_SETRESGID, 0)) != 0) {
+ goto done;
+ }
if (egid != (gid_t)-1 && cr->cr_groups[0] != egid) {
cr = cratom(&p->p_ucred);
cr->cr_svgid = sgid;
setsugid();
}
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_getresuid(struct getresuid_args *uap)
{
struct proc *p = curproc;
- struct ucred *cr = p->p_ucred;
+ struct ucred *cr;
int error1 = 0, error2 = 0, error3 = 0;
+ get_mplock();
+ cr = p->p_ucred;
if (uap->ruid)
error1 = copyout((caddr_t)&cr->cr_ruid,
(caddr_t)uap->ruid, sizeof(cr->cr_ruid));
if (uap->suid)
error3 = copyout((caddr_t)&cr->cr_svuid,
(caddr_t)uap->suid, sizeof(cr->cr_svuid));
+ rel_mplock();
return error1 ? error1 : (error2 ? error2 : error3);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_getresgid(struct getresgid_args *uap)
{
struct proc *p = curproc;
- struct ucred *cr = p->p_ucred;
+ struct ucred *cr;
int error1 = 0, error2 = 0, error3 = 0;
+ get_mplock();
+ cr = p->p_ucred;
if (uap->rgid)
error1 = copyout((caddr_t)&cr->cr_rgid,
(caddr_t)uap->rgid, sizeof(cr->cr_rgid));
if (uap->sgid)
error3 = copyout((caddr_t)&cr->cr_svgid,
(caddr_t)uap->sgid, sizeof(cr->cr_svgid));
+ rel_mplock();
return error1 ? error1 : (error2 ? error2 : error3);
}
-/* ARGSUSED */
+/*
+ * NOTE: OpenBSD sets a P_SUGIDEXEC flag set at execve() time,
+ * we use P_SUGID because we consider changing the owners as
+ * "tainting" as well.
+ * This is significant for procs that start as root and "become"
+ * a user without an exec - programs cannot know *everything*
+ * that libc *might* have put in their data segment.
+ *
+ * MPSAFE
+ */
int
sys_issetugid(struct issetugid_args *uap)
{
- struct proc *p = curproc;
- /*
- * Note: OpenBSD sets a P_SUGIDEXEC flag set at execve() time,
- * we use P_SUGID because we consider changing the owners as
- * "tainting" as well.
- * This is significant for procs that start as root and "become"
- * a user without an exec - programs cannot know *everything*
- * that libc *might* have put in their data segment.
- */
- uap->sysmsg_result = (p->p_flag & P_SUGID) ? 1 : 0;
+ uap->sysmsg_result = (curproc->p_flag & P_SUGID) ? 1 : 0;
return (0);
}
/*
* Get login name, if available.
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_getlogin(struct getlogin_args *uap)
{
struct proc *p = curproc;
+ char buf[MAXLOGNAME];
+ int error;
- if (uap->namelen > MAXLOGNAME)
+ if (uap->namelen > MAXLOGNAME) /* namelen is unsigned */
uap->namelen = MAXLOGNAME;
- return (copyout((caddr_t) p->p_pgrp->pg_session->s_login,
- (caddr_t) uap->namebuf, uap->namelen));
+ get_mplock();
+ bzero(buf, sizeof(buf));
+ bcopy(p->p_pgrp->pg_session->s_login, buf, uap->namelen);
+ rel_mplock();
+
+ error = copyout(buf, uap->namebuf, uap->namelen);
+ return (error);
}
/*
* Set login name.
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_setlogin(struct setlogin_args *uap)
{
struct proc *p = curproc;
+ char buf[MAXLOGNAME];
int error;
- char logintmp[MAXLOGNAME];
KKASSERT(p != NULL);
if ((error = priv_check_cred(p->p_ucred, PRIV_PROC_SETLOGIN, 0)))
return (error);
- error = copyinstr((caddr_t) uap->namebuf, (caddr_t) logintmp,
- sizeof(logintmp), NULL);
+ bzero(buf, sizeof(buf));
+ error = copyinstr(uap->namebuf, buf, sizeof(buf), NULL);
if (error == ENAMETOOLONG)
error = EINVAL;
- else if (!error)
- (void) memcpy(p->p_pgrp->pg_session->s_login, logintmp,
- sizeof(logintmp));
+ if (error == 0) {
+ get_mplock();
+ memcpy(p->p_pgrp->pg_session->s_login, buf, sizeof(buf));
+ rel_mplock();
+ }
return (error);
}
static int getpriority_callback(struct proc *p, void *data);
+/*
+ * MPALMOSTSAFE
+ */
int
sys_getpriority(struct getpriority_args *uap)
{
struct proc *curp = curproc;
struct proc *p;
int low = PRIO_MAX + 1;
+ int error;
+
+ get_mplock();
switch (uap->which) {
case PRIO_PROCESS:
break;
default:
- return (EINVAL);
+ error = EINVAL;
+ goto done;
+ }
+ if (low == PRIO_MAX + 1) {
+ error = ESRCH;
+ goto done;
}
- if (low == PRIO_MAX + 1)
- return (ESRCH);
uap->sysmsg_result = low;
- return (0);
+ error = 0;
+done:
+ rel_mplock();
+ return (error);
}
/*
static int setpriority_callback(struct proc *p, void *data);
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setpriority(struct setpriority_args *uap)
{
struct proc *p;
int found = 0, error = 0;
+ get_mplock();
+
switch (uap->which) {
case PRIO_PROCESS:
if (uap->who == 0)
break;
default:
- return (EINVAL);
+ error = EINVAL;
+ found = 1;
+ break;
}
+
+ rel_mplock();
if (found == 0)
- return (ESRCH);
+ error = ESRCH;
return (error);
}
return (0);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_lwp_rtprio(struct lwp_rtprio_args *uap)
{
error = copyin(uap->rtp, &rtp, sizeof(struct rtprio));
if (error)
return error;
-
- if (uap->pid < 0) {
+ if (uap->pid < 0)
return EINVAL;
- } else if (uap->pid == 0) {
+
+ get_mplock();
+ if (uap->pid == 0) {
/* curproc already loaded on p */
} else {
p = pfind(uap->pid);
}
- if (p == 0) {
- return ESRCH;
+ if (p == NULL) {
+ error = ESRCH;
+ goto done;
}
if (uap->tid < -1) {
- return EINVAL;
- } else if (uap->tid == -1) {
+ error = EINVAL;
+ goto done;
+ }
+ if (uap->tid == -1) {
/*
* sadly, tid can be 0 so we can't use 0 here
* like sys_rtprio()
lp = curthread->td_lwp;
} else {
lp = lwp_rb_tree_RB_LOOKUP(&p->p_lwp_tree, uap->tid);
- if (lp == NULL)
- return ESRCH;
+ if (lp == NULL) {
+ error = ESRCH;
+ goto done;
+ }
}
switch (uap->function) {
case RTP_LOOKUP:
- return (copyout(&lp->lwp_rtprio, uap->rtp,
- sizeof(struct rtprio)));
+ error = copyout(&lp->lwp_rtprio, uap->rtp,
+ sizeof(struct rtprio));
+ break;
case RTP_SET:
if (cr->cr_uid && cr->cr_ruid &&
cr->cr_uid != p->p_ucred->cr_uid &&
cr->cr_ruid != p->p_ucred->cr_uid) {
- return EPERM;
+ error = EPERM;
+ break;
}
/* disallow setting rtprio in most cases if not superuser */
if (priv_check_cred(cr, PRIV_SCHED_RTPRIO, 0)) {
/* can't set someone else's */
if (uap->pid) { /* XXX */
- return EPERM;
+ error = EPERM;
+ break;
}
/* can't set realtime priority */
/*
* due to a CPU-bound normal process). Fix me! XXX
*/
if (RTP_PRIO_IS_REALTIME(rtp.type)) {
- return EPERM;
+ error = EPERM;
+ break;
}
}
switch (rtp.type) {
if (rtp.prio > RTP_PRIO_MAX)
return EINVAL;
lp->lwp_rtprio = rtp;
- return 0;
+ error = 0;
+ break;
default:
- return EINVAL;
+ error = EINVAL;
+ break;
}
+ break;
default:
- return EINVAL;
+ error = EINVAL;
+ break;
}
- panic("can't get here");
+
+done:
+ rel_mplock();
+ return (error);
}
/*
* Set realtime priority
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_rtprio(struct rtprio_args *uap)
{
if (error)
return (error);
+ get_mplock();
if (uap->pid == 0)
p = curp;
else
p = pfind(uap->pid);
- if (p == 0)
- return (ESRCH);
+ if (p == NULL) {
+ error = ESRCH;
+ goto done;
+ }
/* XXX lwp */
lp = FIRST_LWP_IN_PROC(p);
switch (uap->function) {
case RTP_LOOKUP:
- return (copyout(&lp->lwp_rtprio, uap->rtp, sizeof(struct rtprio)));
+ error = copyout(&lp->lwp_rtprio, uap->rtp,
+ sizeof(struct rtprio));
+ break;
case RTP_SET:
if (cr->cr_uid && cr->cr_ruid &&
cr->cr_uid != p->p_ucred->cr_uid &&
- cr->cr_ruid != p->p_ucred->cr_uid)
- return (EPERM);
+ cr->cr_ruid != p->p_ucred->cr_uid) {
+ error = EPERM;
+ break;
+ }
/* disallow setting rtprio in most cases if not superuser */
if (priv_check_cred(cr, PRIV_SCHED_RTPRIO, 0)) {
/* can't set someone else's */
- if (uap->pid)
- return (EPERM);
+ if (uap->pid) {
+ error = EPERM;
+ break;
+ }
/* can't set realtime priority */
/*
* Realtime priority has to be restricted for reasons which should be
* that other processes need (and the idleprio process can't run
* due to a CPU-bound normal process). Fix me! XXX
*/
- if (RTP_PRIO_IS_REALTIME(rtp.type))
- return (EPERM);
+ if (RTP_PRIO_IS_REALTIME(rtp.type)) {
+ error = EPERM;
+ break;
+ }
}
switch (rtp.type) {
#ifdef RTP_PRIO_FIFO
case RTP_PRIO_REALTIME:
case RTP_PRIO_NORMAL:
case RTP_PRIO_IDLE:
- if (rtp.prio > RTP_PRIO_MAX)
- return (EINVAL);
+ if (rtp.prio > RTP_PRIO_MAX) {
+ error = EINVAL;
+ break;
+ }
lp->lwp_rtprio = rtp;
- return (0);
+ error = 0;
+ break;
default:
- return (EINVAL);
+ error = EINVAL;
+ break;
}
-
+ break;
default:
- return (EINVAL);
+ error = EINVAL;
+ break;
}
+done:
+ rel_mplock();
+ return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_setrlimit(struct __setrlimit_args *uap)
{
return (error);
}
+/*
+ * MPSAFE
+ */
int
sys_getrlimit(struct __getrlimit_args *uap)
{
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_getrusage(struct getrusage_args *uap)
{
struct rusage ru;
struct rusage *rup;
+ int error;
- switch (uap->who) {
+ get_mplock();
+ switch (uap->who) {
case RUSAGE_SELF:
rup = &ru;
calcru_proc(curproc, rup);
+ error = 0;
break;
-
case RUSAGE_CHILDREN:
rup = &curproc->p_cru;
+ error = 0;
break;
-
default:
- return (EINVAL);
+ error = EINVAL;
+ break;
}
- return (copyout((caddr_t)rup, (caddr_t)uap->rusage,
- sizeof (struct rusage)));
+ if (error == 0)
+ error = copyout(rup, uap->rusage, sizeof(struct rusage));
+ rel_mplock();
+ return (error);
}
void
return getscheduler(ret, ksched, lp);
}
-/* ksched_yield: Yield the CPU.
+/*
+ * ksched_yield: Yield the CPU.
+ *
+ * MPSAFE
*/
-int ksched_yield(register_t *ret, struct ksched *ksched)
+int
+ksched_yield(register_t *ret, struct ksched *ksched)
{
struct lwp *lp;
return 0;
}
-int ksched_get_priority_max(register_t*ret, struct ksched *ksched, int policy)
+/*
+ * MPSAFE
+ */
+int
+ksched_get_priority_max(register_t*ret, struct ksched *ksched, int policy)
{
int e = 0;
- switch (policy)
- {
- case SCHED_FIFO:
- case SCHED_RR:
+ switch (policy) {
+ case SCHED_FIFO:
+ case SCHED_RR:
*ret = RTP_PRIO_MAX;
break;
-
- case SCHED_OTHER:
+ case SCHED_OTHER:
*ret = PRIO_MAX;
break;
-
- default:
+ default:
e = EINVAL;
+ break;
}
return e;
}
-int ksched_get_priority_min(register_t *ret, struct ksched *ksched, int policy)
+/*
+ * MPSAFE
+ */
+int
+ksched_get_priority_min(register_t *ret, struct ksched *ksched, int policy)
{
int e = 0;
- switch (policy)
- {
- case SCHED_FIFO:
- case SCHED_RR:
+ switch (policy) {
+ case SCHED_FIFO:
+ case SCHED_RR:
*ret = P1B_PRIO_MIN;
break;
-
- case SCHED_OTHER:
+ case SCHED_OTHER:
*ret = PRIO_MIN;
break;
-
- default:
+ default:
e = EINVAL;
+ break;
}
-
return e;
}
-int ksched_rr_get_interval(register_t *ret, struct ksched *ksched,
- struct lwp *lp, struct timespec *timespec)
+/*
+ * MPSAFE
+ */
+int
+ksched_rr_get_interval(register_t *ret, struct ksched *ksched,
+ struct lwp *lp, struct timespec *timespec)
{
*timespec = ksched->rr_interval;
/*
* The system call that results in a reboot
+ *
+ * MPALMOSTSAFE
*/
int
sys_reboot(struct reboot_args *uap)
if ((error = priv_check(td, PRIV_REBOOT)))
return (error);
+ get_mplock();
boot(uap->opt);
+ rel_mplock();
return (0);
}
return (0);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sigaction(struct sigaction_args *uap)
{
if (error)
return (error);
}
+ get_mplock();
error = kern_sigaction(uap->sig, actp, oactp);
+ rel_mplock();
if (oactp && !error) {
error = copyout(oactp, uap->oact, sizeof(oact));
}
}
/*
- * sigprocmask() - MP SAFE
+ * sigprocmask()
+ *
+ * MPSAFE
*/
int
sys_sigprocmask(struct sigprocmask_args *uap)
return (error);
}
+/*
+ * MPSAFE
+ */
int
kern_sigpending(struct __sigset *set)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_sigpending(struct sigpending_args *uap)
{
/*
* Suspend process until signal, providing mask to be set
* in the meantime.
+ *
+ * MPSAFE
*/
int
kern_sigsuspend(struct __sigset *set)
/*
* Note nonstandard calling convention: libc stub passes mask, not
* pointer, to save a copyin.
+ *
+ * MPSAFE
*/
int
sys_sigsuspend(struct sigsuspend_args *uap)
return (error);
}
+/*
+ * MPSAFE
+ */
int
kern_sigaltstack(struct sigaltstack *ss, struct sigaltstack *oss)
{
return (0);
}
+/*
+ * MPSAFE
+ */
int
sys_sigaltstack(struct sigaltstack_args *uap)
{
/* NOTREACHED */
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_kill(struct kill_args *uap)
{
int error;
+ get_mplock();
error = kern_kill(uap->signum, uap->pid, -1);
+ rel_mplock();
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_lwp_kill(struct lwp_kill_args *uap)
{
if (pid == -1)
pid = curproc->p_pid;
+ get_mplock();
error = kern_kill(uap->signum, pid, uap->tid);
+ rel_mplock();
return (error);
}
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sigtimedwait(struct sigtimedwait_args *uap)
{
error = copyin(uap->set, &set, sizeof(set));
if (error)
return (error);
+ get_mplock();
error = kern_sigtimedwait(set, &info, timeout);
+ rel_mplock();
if (error)
return (error);
if (uap->info)
* This could transform a thread-specific signal to another
* thread / process pending signal.
*/
- if (error)
+ if (error) {
+ get_mplock();
ksignal(curproc, info.si_signo);
- else
+ rel_mplock();
+ } else {
uap->sysmsg_result = info.si_signo;
+ }
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_sigwaitinfo(struct sigwaitinfo_args *uap)
{
error = copyin(uap->set, &set, sizeof(set));
if (error)
return (error);
+ get_mplock();
error = kern_sigtimedwait(set, &info, NULL);
+ rel_mplock();
if (error)
return (error);
if (uap->info)
* This could transform a thread-specific signal to another
* thread / process pending signal.
*/
- if (error)
+ if (error) {
+ get_mplock();
ksignal(curproc, info.si_signo);
- else
+ rel_mplock();
+ } else {
uap->sysmsg_result = info.si_signo;
+ }
return (error);
}
/*
* Nonexistent system call-- signal process (may want to handle it).
* Flag error in case process won't see signal immediately (blocked or ignored).
+ *
+ * MPALMOSTSAFE
*/
/* ARGSUSED */
int
sys_nosys(struct nosys_args *args)
{
+ get_mplock();
lwpsignal(curproc, curthread->td_lwp, SIGSYS);
+ rel_mplock();
return (EINVAL);
}
* it's call to lwkt_maybe_switch() in acquire_curproc() will likely
* round-robin back to us and we will be able to re-acquire the current
* process designation.
+ *
+ * MPSAFE
*/
void
uio_yield(void)
return (error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys___sysctl(struct sysctl_args *uap)
{
if (error)
return (error);
+ get_mplock();
error = userland_sysctl(name, uap->namelen,
uap->old, uap->oldlenp, 0,
uap->new, uap->newlen, &j);
+ rel_mplock();
if (error && error != ENOMEM)
return (error);
if (uap->oldlenp) {
************************************************************************
*
* syslink(int cmd, struct syslink_info *info, size_t bytes)
+ *
+ * MPALMOSTSAFE
*/
int
sys_syslink(struct syslink_args *uap)
}
if (error)
return (error);
+ get_mplock();
/*
* Process the command
error = EINVAL;
break;
}
+
+ rel_mplock();
if (error == 0 && info.head.wbflag)
copyout(&info, uap->info, uap->bytes);
return (error);
cputimer_intr_enable();
}
+/*
+ * MPSAFE
+ */
void
systimer_add(systimer_t info)
{
* systimer_del()
*
* Delete a system timer. Only the owning cpu can delete a timer.
+ *
+ * MPSAFE
*/
void
systimer_del(systimer_t info)
#include <sys/sysproto.h>
#include <sys/uio.h> /* uio_yield() fixme */
+#if 0
/*
* XXX lwp
return 0;
}
+#endif
+
/*
* General purpose yield system call
+ *
+ * MPSAFE
*/
int
sys_yield(struct yield_args *uap)
return (0);
}
+/*
+ * MPSAFE
+ */
int
kern_clock_gettime(clockid_t clock_id, struct timespec *ats)
{
return (error);
}
-/* ARGSUSED */
+/*
+ * MPSAFE
+ */
int
sys_clock_gettime(struct clock_gettime_args *uap)
{
return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_clock_settime(struct clock_settime_args *uap)
{
if ((error = copyin(uap->tp, &ats, sizeof(ats))) != 0)
return (error);
- return (kern_clock_settime(uap->clock_id, &ats));
+ get_mplock();
+ error = kern_clock_settime(uap->clock_id, &ats);
+ rel_mplock();
+ return (error);
}
+/*
+ * MPSAFE
+ */
int
kern_clock_getres(clockid_t clock_id, struct timespec *ts)
{
return(error);
}
+/*
+ * MPSAFE
+ */
int
sys_clock_getres(struct clock_getres_args *uap)
{
* tsleep, then handle the fine-grained delay on the next
* loop. This usually results in two sleeps occuring, a long one
* and a short one.
+ *
+ * MPSAFE
*/
static void
ns1_systimer(systimer_t info)
}
}
-/* ARGSUSED */
+/*
+ * MPSAFE
+ */
int
sys_nanosleep(struct nanosleep_args *uap)
{
return (error);
}
-/* ARGSUSED */
+/*
+ * MPSAFE
+ */
int
sys_gettimeofday(struct gettimeofday_args *uap)
{
return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_settimeofday(struct settimeofday_args *uap)
{
if (uap->tzp &&
(error = copyin((caddr_t)uap->tzp, (caddr_t)&atz, sizeof(atz))))
return (error);
- if (uap->tv && (error = settime(&atv)))
+
+ get_mplock();
+ if (uap->tv && (error = settime(&atv))) {
+ rel_mplock();
return (error);
+ }
+ rel_mplock();
if (uap->tzp)
tz = atz;
return (0);
lwkt_setcpu_self(globaldata_find(origcpu));
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_adjtime(struct adjtime_args *uap)
{
if ((error = priv_check(td, PRIV_ADJTIME)))
return (error);
- if ((error =
- copyin((caddr_t)uap->delta, (caddr_t)&atv, sizeof(struct timeval))))
+ error = copyin(uap->delta, &atv, sizeof(struct timeval));
+ if (error)
return (error);
/*
* overshoot and start taking us away from the desired final time.
*/
ndelta = (int64_t)atv.tv_sec * 1000000000 + atv.tv_usec * 1000;
+ get_mplock();
kern_adjtime(ndelta, &odelta);
+ rel_mplock();
if (uap->olddelta) {
atv.tv_sec = odelta / 1000000000;
atv.tv_usec = odelta % 1000000000 / 1000;
- (void) copyout((caddr_t)&atv, (caddr_t)uap->olddelta,
- sizeof(struct timeval));
+ copyout(&atv, uap->olddelta, sizeof(struct timeval));
}
return (0);
}
* does not suffice, therefore, to reload the real timer .it_value from the
* real time timers .it_interval. Rather, we compute the next time in
* absolute time the timer should go off.
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_getitimer(struct getitimer_args *uap)
{
if (uap->which > ITIMER_PROF)
return (EINVAL);
+ get_mplock();
crit_enter();
if (uap->which == ITIMER_REAL) {
/*
aitv = p->p_timer[uap->which];
}
crit_exit();
- return (copyout((caddr_t)&aitv, (caddr_t)uap->itv,
- sizeof (struct itimerval)));
+ rel_mplock();
+ return (copyout(&aitv, uap->itv, sizeof (struct itimerval)));
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setitimer(struct setitimer_args *uap)
{
timevalclear(&aitv.it_interval);
else if (itimerfix(&aitv.it_interval))
return (EINVAL);
+ get_mplock();
crit_enter();
if (uap->which == ITIMER_REAL) {
if (timevalisset(&p->p_realtimer.it_value))
p->p_timer[uap->which] = aitv;
}
crit_exit();
+ rel_mplock();
return (0);
}
* .it_interval part of an interval timer is acceptable, and
* fix it to have at least minimal value (i.e. if it is less
* than the resolution of the clock, round it up.)
+ *
+ * MPSAFE
*/
int
itimerfix(struct timeval *tv)
* copy-on-write. We register an event on the VM page to catch COWs.
*
* umtx_sleep { const int *ptr, int value, int timeout }
+ *
+ * MPALMOSTSAFE
*/
int
sys_umtx_sleep(struct umtx_sleep_args *uap)
* Otherwise the physical page we sleep on my not match the page
* being woken up.
*/
+ get_mplock();
m = vm_fault_page_quick((vm_offset_t)uap->ptr, VM_PROT_READ|VM_PROT_WRITE, &error);
- if (m == NULL)
- return (EFAULT);
+ if (m == NULL) {
+ error = EFAULT;
+ goto done;
+ }
sf = sf_buf_alloc(m, SFB_CPUPRIVATE);
offset = (vm_offset_t)uap->ptr & PAGE_MASK;
sf_buf_free(sf);
/*vm_page_dirty(m); we don't actually dirty the page */
vm_page_unhold(m);
+done:
+ rel_mplock();
return(error);
}
*
* XXX assumes that the physical address space does not exceed the virtual
* address space.
+ *
+ * MPALMOSTSAFE
*/
int
sys_umtx_wakeup(struct umtx_wakeup_args *uap)
cpu_mfence();
if ((vm_offset_t)uap->ptr & (sizeof(int) - 1))
return (EFAULT);
+ get_mplock();
m = vm_fault_page_quick((vm_offset_t)uap->ptr, VM_PROT_READ, &error);
- if (m == NULL)
- return (EFAULT);
+ if (m == NULL) {
+ error = EFAULT;
+ goto done;
+ }
offset = (vm_offset_t)uap->ptr & PAGE_MASK;
waddr = (void *)((intptr_t)VM_PAGE_TO_PHYS(m) + offset);
wakeup_domain(waddr, PDOMAIN_UMTX);
}
vm_page_unhold(m);
- return(0);
+ error = 0;
+done:
+ rel_mplock();
+ return(error);
}
* upcall context is set globally for the process, not for each upcall.
*
* ARGS(struct upcall *upc, upcall_func_t ctx, upcall_func_t func, void *data)
+ *
+ * MPALMOSTSAFE
*/
int
sys_upc_register(struct upc_register_args *uap)
struct vmspace *vm = curproc->p_vmspace;
struct vmupcall *vu;
+ /*
+ * Note: inconsequential MP race
+ */
if (vm->vm_upccount >= UPCALL_MAXCOUNT)
return(EFBIG);
vu->vu_lwp = lp;
lp->lwp_upcall = uap->upc;
+ get_mplock();
if (vm->vm_upcalls != NULL)
vu->vu_id = vm->vm_upcalls->vu_id + 1;
else
vu->vu_next = vm->vm_upcalls;
vm->vm_upcalls = vu;
++vm->vm_upccount;
+ rel_mplock();
uap->sysmsg_result = vu->vu_id;
return(0);
}
* upc_control:
*
* ARGS(int cmd, int upcid, void *data)
+ *
+ * MPALMOSTSAFE
*/
int
sys_upc_control(struct upc_control_args *uap)
struct vmupcall **vupp;
int error;
+ get_mplock();
switch(uap->cmd) {
case UPC_CONTROL_DISPATCH:
/*
error = EINVAL;
break;
}
+ rel_mplock();
return(error);
}
* RETURN VALUES:
* 0 - success
* EINVAL - error
+ *
+ * MPALMOSTSAFE
*/
int
sys_usched_set(struct usched_set_args *uap)
cpumask_t mask;
struct lwp *lp;
int cpuid;
+
if (uap->pid != 0 && uap->pid != curthread->td_proc->p_pid)
return (EINVAL);
lp = curthread->td_lwp;
+ get_mplock();
+
switch (uap->cmd) {
case USCHED_SET_SCHEDULER:
if ((error = priv_check(curthread, PRIV_SCHED_SET)) != 0)
- return (error);
- if ((error = copyinstr(uap->data, buffer, sizeof(buffer),
- NULL)) != 0)
- return (error);
+ break;
+ error = copyinstr(uap->data, buffer, sizeof(buffer), NULL);
+ if (error)
+ break;
TAILQ_FOREACH(item, &usched_list, entry) {
if ((strcmp(item->name, buffer) == 0))
break;
* reassociation'
*/
/* XXX lwp have to deal with multiple lwps here */
- if (p->p_nthreads != 1)
- return (EINVAL);
+ if (p->p_nthreads != 1) {
+ error = EINVAL;
+ break;
+ }
if (item && item != p->p_usched) {
/* XXX lwp */
p->p_usched->release_curproc(ONLY_LWP_IN_PROC(p));
break;
case USCHED_SET_CPU:
if ((error = priv_check(curthread, PRIV_SCHED_CPUSET)) != 0)
- return (error);
- if (uap->bytes != sizeof(int))
- return (EINVAL);
+ break;
+ if (uap->bytes != sizeof(int)) {
+ error = EINVAL;
+ break;
+ }
error = copyin(uap->data, &cpuid, sizeof(int));
if (error)
break;
break;
case USCHED_GET_CPU:
/* USCHED_GET_CPU doesn't require special privileges. */
- if (uap->bytes != sizeof(int))
- return (EINVAL);
+ if (uap->bytes != sizeof(int)) {
+ error = EINVAL;
+ break;
+ }
error = copyout(&(mycpu->gd_cpuid), uap->data, sizeof(int));
break;
case USCHED_ADD_CPU:
if ((error = priv_check(curthread, PRIV_SCHED_CPUSET)) != 0)
- return (error);
- if (uap->bytes != sizeof(int))
- return (EINVAL);
+ break;
+ if (uap->bytes != sizeof(int)) {
+ error = EINVAL;
+ break;
+ }
error = copyin(uap->data, &cpuid, sizeof(int));
if (error)
break;
break;
case USCHED_DEL_CPU:
/* USCHED_DEL_CPU doesn't require special privileges. */
- if (uap->bytes != sizeof(int))
- return (EINVAL);
+ if (uap->bytes != sizeof(int)) {
+ error = EINVAL;
+ break;
+ }
error = copyin(uap->data, &cpuid, sizeof(int));
if (error)
break;
error = EINVAL;
break;
}
+ rel_mplock();
return (error);
}
* uuidgen(struct uuid *store, int count)
*
* Generate an array of new UUIDs
+ *
+ * MPALMOSTSAFE
*/
int
sys_uuidgen(struct uuidgen_args *uap)
count = uap->count;
store = kmalloc(count * sizeof(struct uuid), M_TEMP, M_WAITOK);
+ get_mplock();
kern_uuidgen(store, count);
+ rel_mplock();
error = copyout(store, uap->store, count * sizeof(struct uuid));
kfree(store, M_TEMP);
return (error);
* varsym_set() system call
*
* (int level, const char *name, const char *data)
+ *
+ * MPALMOSTSAFE
*/
int
sys_varsym_set(struct varsym_set_args *uap)
{
goto done1;
}
+
+ get_mplock();
+
switch(uap->level) {
case VARSYM_SYS:
if (p != NULL && p->p_ucred->cr_prison != NULL)
}
break;
}
+ rel_mplock();
done1:
kfree(buf, M_TEMP);
done2:
* varsym_get() system call
*
* (int mask, const char *wild, char *buf, int bufsize)
+ *
+ * MPALMOSTSAFE
*/
int
sys_varsym_get(struct varsym_get_args *uap)
int error;
int dlen;
+ get_mplock();
if ((error = copyinstr(uap->wild, wild, sizeof(wild), NULL)) != 0)
goto done;
sym = varsymfind(uap->mask, wild, strlen(wild));
uap->sysmsg_result = dlen + 1;
varsymdrop(sym);
done:
+ rel_mplock();
return(error);
}
* varsym_list() system call
*
* (int level, char *buf, int maxsize, int *marker)
+ *
+ * MPALMOSTSAFE
*/
int
sys_varsym_list(struct varsym_list_args *uap)
/*
* Get the marker from userspace.
*/
+ get_mplock();
if ((error = copyin(uap->marker, &marker, sizeof(marker))) != 0)
goto done;
error = copyout(&marker, uap->marker, sizeof(marker));
uap->sysmsg_result = bytes;
done:
+ rel_mplock();
return(error);
}
#include <sys/sysctl.h>
#include <sys/utsname.h>
-/* ARGSUSED */
-/* MP SAFE */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_uname(struct uname_args *uap)
{
size_t len;
char *s, *us;
+ get_mplock();
+
name[0] = CTL_KERN;
name[1] = KERN_OSTYPE;
len = sizeof uap->name->sysname;
rtval = userland_sysctl(name, 2, uap->name->sysname, &len,
1, 0, 0, 0);
- if( rtval) return rtval;
+ if (rtval)
+ goto done;
subyte( uap->name->sysname + sizeof(uap->name->sysname) - 1, 0);
name[1] = KERN_HOSTNAME;
len = sizeof uap->name->nodename;
rtval = userland_sysctl(name, 2, uap->name->nodename, &len,
1, 0, 0, 0);
- if( rtval) return rtval;
+ if (rtval)
+ goto done;
subyte( uap->name->nodename + sizeof(uap->name->nodename) - 1, 0);
name[1] = KERN_OSRELEASE;
len = sizeof uap->name->release;
rtval = userland_sysctl(name, 2, uap->name->release, &len,
1, 0, 0, 0);
- if( rtval) return rtval;
+ if (rtval)
+ goto done;
subyte( uap->name->release + sizeof(uap->name->release) - 1, 0);
/*
len = sizeof uap->name->version;
rtval = userland_sysctl(name, 2, uap->name->version, &len,
1, 0, 0, 0);
- if( rtval) return rtval;
+ if (rtval)
+ goto done;
subyte( uap->name->version + sizeof(uap->name->version) - 1, 0);
*/
for(us = uap->name->version; *s && *s != ':'; s++) {
rtval = subyte( us++, *s);
- if( rtval)
- return rtval;
+ if (rtval)
+ goto done;
}
rtval = subyte( us++, 0);
- if( rtval)
- return rtval;
+ if (rtval)
+ goto done;
name[0] = CTL_HW;
name[1] = HW_MACHINE;
len = sizeof uap->name->machine;
rtval = userland_sysctl(name, 2, uap->name->machine, &len,
1, 0, 0, 0);
- if( rtval) return rtval;
- subyte( uap->name->machine + sizeof(uap->name->machine) - 1, 0);
-
- return 0;
+ if (rtval)
+ goto done;
+ rtval = subyte(uap->name->machine + sizeof(uap->name->machine) - 1, 0);
+done:
+ rel_mplock();
+ return rtval;
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_getdomainname(struct getdomainname_args *uap)
{
- int domainnamelen = strlen(domainname) + 1;
+ int domainnamelen;
+ int error;
+
+ get_mplock();
+ domainnamelen = strlen(domainname) + 1;
if ((u_int)uap->len > domainnamelen + 1)
uap->len = domainnamelen + 1;
- return (copyout((caddr_t)domainname, (caddr_t)uap->domainname, uap->len));
+ error = copyout(domainname, uap->domainname, uap->len);
+ rel_mplock();
+ return (error);
}
-/* ARGSUSED */
+/*
+ * MPALMOSTSAFE
+ */
int
sys_setdomainname(struct setdomainname_args *uap)
{
if ((error = priv_check(td, PRIV_SETDOMAINNAME)))
return (error);
- if ((u_int)uap->len > sizeof (domainname) - 1)
+ if ((u_int)uap->len > sizeof(domainname) - 1)
return EINVAL;
+ get_mplock();
domainnamelen = uap->len;
- error = copyin((caddr_t)uap->domainname, domainname, uap->len);
+ error = copyin(uap->domainname, domainname, uap->len);
domainname[domainnamelen] = 0;
+ rel_mplock();
return (error);
}
* returned.
*
* upcid can either be an upcall or a kqueue identifier (XXX)
+ *
+ * MPALMOSTSAFE
*/
int
sys_caps_sys_service(struct caps_sys_service_args *uap)
return(error);
if ((ssize_t)--len <= 0)
return(EINVAL);
- if ((error = caps_name_check(name, len)) != 0)
- return(error);
+ get_mplock();
- caps = kern_caps_sys_service(name, uap->uid, uap->gid, cred,
- uap->flags & CAPF_UFLAGS, &error);
- if (caps)
- uap->sysmsg_result = caps->ci_id;
+ if ((error = caps_name_check(name, len)) == 0) {
+ caps = kern_caps_sys_service(name, uap->uid, uap->gid, cred,
+ uap->flags & CAPF_UFLAGS, &error);
+ if (caps)
+ uap->sysmsg_result = caps->ci_id;
+ }
+ rel_mplock();
return(error);
}
* returned.
*
* upcid can either be an upcall or a kqueue identifier (XXX)
+ *
+ * MPALMOSTSAFE
*/
int
sys_caps_sys_client(struct caps_sys_client_args *uap)
return(error);
if ((ssize_t)--len <= 0)
return(EINVAL);
- if ((error = caps_name_check(name, len)) != 0)
- return(error);
+ get_mplock();
- caps = kern_caps_sys_client(name, uap->uid, uap->gid, cred,
- uap->flags & CAPF_UFLAGS, &error);
- if (caps)
- uap->sysmsg_result = caps->ci_id;
+ if ((error = caps_name_check(name, len)) == 0) {
+ caps = kern_caps_sys_client(name, uap->uid, uap->gid, cred,
+ uap->flags & CAPF_UFLAGS, &error);
+ if (caps)
+ uap->sysmsg_result = caps->ci_id;
+ }
+ rel_mplock();
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_caps_sys_close(struct caps_sys_close_args *uap)
{
caps_kinfo_t caps;
+ int error;
- if ((caps = caps_find_id(curthread, uap->portid)) == NULL)
- return(EINVAL);
- caps_term(caps, CAPKF_TDLIST|CAPKF_HLIST|CAPKF_FLUSH|CAPKF_RCAPS, NULL);
- caps_drop(caps);
- return(0);
+ get_mplock();
+
+ if ((caps = caps_find_id(curthread, uap->portid)) != NULL) {
+ caps_term(caps, CAPKF_TDLIST|CAPKF_HLIST|CAPKF_FLUSH|CAPKF_RCAPS,
+ NULL);
+ caps_drop(caps);
+ error = 0;
+ } else {
+ error = EINVAL;
+ }
+ rel_mplock();
+ return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_caps_sys_setgen(struct caps_sys_setgen_args *uap)
{
caps_kinfo_t caps;
int error;
- if ((caps = caps_find_id(curthread, uap->portid)) == NULL)
- return(EINVAL);
- if (caps->ci_type == CAPT_FORKED) {
- error = ENOTCONN;
+ get_mplock();
+
+ if ((caps = caps_find_id(curthread, uap->portid)) != NULL) {
+ if (caps->ci_type == CAPT_FORKED) {
+ error = ENOTCONN;
+ } else {
+ caps->ci_gen = uap->gen;
+ error = 0;
+ }
+ caps_drop(caps);
} else {
- caps->ci_gen = uap->gen;
- error = 0;
+ error = EINVAL;
}
- caps_drop(caps);
+ rel_mplock();
return(error);
}
+/*
+ * MPALMOSTSAFE
+ */
int
sys_caps_sys_getgen(struct caps_sys_getgen_args *uap)
{
caps_kinfo_t caps;
int error;
- if ((caps = caps_find_id(curthread, uap->portid)) == NULL)
- return(EINVAL);
- if (caps->ci_type == CAPT_FORKED) {
- error = ENOTCONN;
- } else if (caps->ci_rcaps == NULL) {
- error = EINVAL;
+ get_mplock();
+
+ if ((caps = caps_find_id(curthread, uap->portid)) != NULL) {
+ if (caps->ci_type == CAPT_FORKED) {
+ error = ENOTCONN;
+ } else if (caps->ci_rcaps == NULL) {
+ error = EINVAL;
+ } else {
+ uap->sysmsg_result64 = caps->ci_rcaps->ci_gen;
+ error = 0;
+ }
+ caps_drop(caps);
} else {
- uap->sysmsg_result64 = caps->ci_rcaps->ci_gen;
- error = 0;
+ error = EINVAL;
}
- caps_drop(caps);
+ rel_mplock();
return(error);
}
*
* Send an opaque message of the specified size to the specified port. This
* function may only be used with a client port. The message id is returned.
+ *
+ * MPALMOSTSAFE
*/
int
sys_caps_sys_put(struct caps_sys_put_args *uap)
if (uap->msgsize < 0)
return(EINVAL);
- if ((caps = caps_find_id(curthread, uap->portid)) == NULL)
- return(EINVAL);
+ get_mplock();
+
+ if ((caps = caps_find_id(curthread, uap->portid)) == NULL) {
+ error = EINVAL;
+ goto done;
+ }
if (caps->ci_type == CAPT_FORKED) {
error = ENOTCONN;
} else if (caps->ci_rcaps == NULL) {
}
}
caps_drop(caps);
+done:
+ rel_mplock();
return(error);
}
*
* Reply to the message referenced by the specified msgid, supplying opaque
* data back to the originator.
+ *
+ * MPALMOSTSAFE
*/
int
sys_caps_sys_reply(struct caps_sys_reply_args *uap)
if (uap->msgsize < 0)
return(EINVAL);
- if ((caps = caps_find_id(curthread, uap->portid)) == NULL)
- return(EINVAL);
+ get_mplock();
+
+ if ((caps = caps_find_id(curthread, uap->portid)) == NULL) {
+ error = EINVAL;
+ goto done;
+ }
if (caps->ci_type == CAPT_FORKED) {
/*
* The caps structure is just a fork placeholder, tell the caller
}
}
caps_drop(caps);
+done:
+ rel_mplock();
return(error);
}
*
* EWOULDBLOCK is returned if no messages are pending. Note that 0-length
* messages are perfectly acceptable so 0 can be legitimately returned.
+ *
+ * MPALMOSTSAFE
*/
int
sys_caps_sys_get(struct caps_sys_get_args *uap)
if (uap->maxsize < 0)
return(EINVAL);
- if ((caps = caps_find_id(curthread, uap->portid)) == NULL)
- return(EINVAL);
- if (caps->ci_type == CAPT_FORKED) {
- error = ENOTCONN;
- } else if ((msg = TAILQ_FIRST(&caps->ci_msgpendq)) == NULL) {
- error = EWOULDBLOCK;
+ get_mplock();
+
+ if ((caps = caps_find_id(curthread, uap->portid)) != NULL) {
+ if (caps->ci_type == CAPT_FORKED) {
+ error = ENOTCONN;
+ } else if ((msg = TAILQ_FIRST(&caps->ci_msgpendq)) == NULL) {
+ error = EWOULDBLOCK;
+ } else {
+ error = caps_process_msg(caps, msg, uap);
+ }
} else {
- error = caps_process_msg(caps, msg, uap);
+ error = EINVAL;
}
caps_drop(caps);
+ rel_mplock();
return(error);
}
* This function blocks until interrupted or a message is received.
* Note that 0-length messages are perfectly acceptable so 0 can be
* legitimately returned.
+ *
+ * MPALMOSTSAFE
*/
int
sys_caps_sys_wait(struct caps_sys_wait_args *uap)
if (uap->maxsize < 0)
return(EINVAL);
- if ((caps = caps_find_id(curthread, uap->portid)) == NULL)
- return(EINVAL);
- if (caps->ci_type == CAPT_FORKED) {
- error = ENOTCONN;
- } else {
- error = 0;
- while ((msg = TAILQ_FIRST(&caps->ci_msgpendq)) == NULL) {
- if ((error = tsleep(caps, PCATCH, "caps", 0)) != 0)
- break;
- }
- if (error == 0) {
- error = caps_process_msg(caps, msg,
- (struct caps_sys_get_args *)uap);
+ get_mplock();
+
+ if ((caps = caps_find_id(curthread, uap->portid)) != NULL) {
+ if (caps->ci_type == CAPT_FORKED) {
+ error = ENOTCONN;
+ } else {
+ error = 0;
+ while ((msg = TAILQ_FIRST(&caps->ci_msgpendq)) == NULL) {
+ if ((error = tsleep(caps, PCATCH, "caps", 0)) != 0)
+ break;
+ }
+ if (error == 0) {
+ error = caps_process_msg(caps, msg,
+ (struct caps_sys_get_args *)uap);
+ }
}
+ } else {
+ error = EINVAL;
}
caps_drop(caps);
+ rel_mplock();
return(error);
}
static int
-caps_process_msg(caps_kinfo_t caps, caps_kmsg_t msg, struct caps_sys_get_args *uap)
+caps_process_msg(caps_kinfo_t caps, caps_kmsg_t msg,
+ struct caps_sys_get_args *uap)
{
int error = 0;
int msgsize;
* to be returned after sending the abort request. This function will
* return the appropriate CAPS_ABORT_* code depending on what it had
* to do.
+ *
+ * MPALMOSTSAFE
*/
int
sys_caps_sys_abort(struct caps_sys_abort_args *uap)
for (i = 5; i <= NF; i++)
comment = comment " " $i
}
- # if the "MPSAFE" keyword is found, note it and shift the line
- mpsafe = ""
- $2 == "MPSAFE" {
- for (i = 2; i <= NF; i++)
- $i = $(i + 1);
- NF -= 1;
- mpsafe = "SYF_MPSAFE | "
- }
$2 == "STD" || $2 == "NODEF" || $2 == "NOARGS" || $2 == "NOPROTO" \
|| $2 == "NOIMPL" {
parseline()
nosys = 1
if (funcname == "lkmnosys")
lkmnosys = 1
- printf("\t{ %s%s, (sy_call_t *)", mpsafe, argssize) > sysent
- column = 8 + 2 + length(mpsafe) + length(argssize) + 15
+ printf("\t{ %s, (sy_call_t *)", argssize) > sysent
+ column = 8 + 2 + length(argssize) + 15
if ($2 != "NOIMPL") {
printf("sys_%s },", funcname) > sysent
column = column + length(funcname) + 7
}
printf("%s\tsys_o%s (struct %s *);\n",
rettype, funcname, argalias) > syscompatdcl
- printf("\t{ compat(%s%s,%s) },",
- mpsafe, argssize, funcname) > sysent
- align_sysent_comment(8 + 9 + length(mpsafe) + \
+ printf("\t{ compat(%s,%s) },",
+ argssize, funcname) > sysent
+ align_sysent_comment(8 + 9 + \
length(argssize) + 1 + length(funcname) + 4)
printf("/* %d = old %s */\n", syscall, funcalias) > sysent
printf("\t\"old.%s\",\t\t/* %d = old %s */\n",
}
printf("%s\tsys_dfbsd12_%s (struct %s *);\n",
rettype, funcname, argalias) > syscompatdcldf12
- printf("\t{ compatdf12(%s%s,%s) },",
- mpsafe, argssize, funcname) > sysent
- align_sysent_comment(8 + 9 + length(mpsafe) + \
+ printf("\t{ compatdf12(%s,%s) },",
+ argssize, funcname) > sysent
+ align_sysent_comment(8 + 9 + \
length(argssize) + 1 + length(funcname) + 4)
printf("/* %d = old %s */\n", syscall, funcalias) > sysent
printf("\t\"old.%s\",\t\t/* %d = old %s */\n",
ncompat++
parseline()
printf("%s\tsys_o%s();\n", rettype, funcname) > syscompatdcl
- printf("\t{ compat(%s%s,%s) },",
- mpsafe, argssize, funcname) > sysent
- align_sysent_comment(8 + 9 + length(mpsafe) + \
+ printf("\t{ compat(%s,%s) },",
+ argssize, funcname) > sysent
+ align_sysent_comment(8 + 9 + \
length(argssize) + 1 + length(funcname) + 4)
printf("/* %d = old %s */\n", syscall, funcalias) > sysent
printf("\t\"old.%s\",\t\t/* %d = old %s */\n",
*
* The scale factor is a fixed point number with 16 bits of fraction, so that
* 1.0 is represented as 0x10000. A scale factor of 0 turns off profiling.
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_profil(struct profil_args *uap)
{
if (uap->scale > (1 << 16))
return (EINVAL);
+ get_mplock();
if (uap->scale == 0) {
stopprofclock(p);
- return (0);
+ } else {
+ upp = &p->p_prof;
+
+ /* Block profile interrupts while changing state. */
+ crit_enter();
+ upp->pr_off = uap->offset;
+ upp->pr_scale = uap->scale;
+ upp->pr_base = uap->samples;
+ upp->pr_size = uap->size;
+ startprofclock(p);
+ crit_exit();
}
- upp = &p->p_prof;
-
- /* Block profile interrupts while changing state. */
- crit_enter();
- upp->pr_off = uap->offset;
- upp->pr_scale = uap->scale;
- upp->pr_base = uap->samples;
- upp->pr_size = uap->size;
- startprofclock(p);
- crit_exit();
-
+ rel_mplock();
return (0);
}
/*
* Ioctl system call
+ *
+ * MPALMOSTSAFE
*/
-/* ARGSUSED */
int
sys_ioctl(struct ioctl_args *uap)
{
- return(mapped_ioctl(uap->fd, uap->com, uap->data, NULL, &uap->sysmsg));
+ int error;
+
+ get_mplock();
+ error = mapped_ioctl(uap->fd, uap->com, uap->data, NULL, &uap->sysmsg);
+ rel_mplock();
+ return (error);
}
struct ioctl_map_entry {
/*
* Select system call.
+ *
+ * MPALMOSTSAFE
*/
int
sys_select(struct select_args *uap)
/*
* Do real work.
*/
+ get_mplock();
error = doselect(uap->nd, uap->in, uap->ou, uap->ex, ktvp,
&uap->sysmsg_result);
+ rel_mplock();
return (error);
}
/*
* Pselect system call.
+ *
+ * MPALMOSTSAFE
*/
int
sys_pselect(struct pselect_args *uap)
error = copyin(uap->sigmask, &sigmask, sizeof(sigmask));
if (error)
return (error);
+ get_mplock();
lp->lwp_oldsigmask = lp->lwp_sigmask;
SIG_CANTMASK(sigmask);
lp->lwp_sigmask = sigmask;
+ } else {
+ get_mplock();
}
/*
lp->lwp_sigmask = lp->lwp_oldsigmask;
}
}
+ rel_mplock();
return (error);
}
/*
* Poll system call.
+ *
+ * MPALMOSTSAFE
*/
int
sys_poll(struct poll_args *uap)
retry:
ncoll = nselcoll;
lp->lwp_flag |= LWP_SELECT;
+ get_mplock();
error = pollscan(p, bits, nfds, &uap->sysmsg_result);
+ rel_mplock();
if (error || uap->sysmsg_result)
goto done;
if (atv.tv_sec || atv.tv_usec) {
24 * 60 * 60 * hz : tvtohz_high(&ttv);
}
crit_enter();
+ tsleep_interlock(&selwait, PCATCH);
if ((lp->lwp_flag & LWP_SELECT) == 0 || nselcoll != ncoll) {
crit_exit();
goto retry;
}
lp->lwp_flag &= ~LWP_SELECT;
- error = tsleep((caddr_t)&selwait, PCATCH, "poll", timo);
+ error = tsleep(&selwait, PCATCH | PINTERLOCKED, "poll", timo);
crit_exit();
if (error == 0)
goto retry;
/*
* OpenBSD poll system call.
* XXX this isn't quite a true representation.. OpenBSD uses select ops.
+ *
+ * MPSAFE
*/
int
sys_openbsd_poll(struct openbsd_poll_args *uap)
/*
* The pipe system call for the DTYPE_PIPE type of pipes
*
- * pipe_ARgs(int dummy)
+ * pipe_args(int dummy)
+ *
+ * MPSAFE
*/
-
-/* ARGSUSED */
int
sys_pipe(struct pipe_args *uap)
{
/*
* Process debugging system call.
+ *
+ * MPALMOSTSAFE
*/
int
sys_ptrace(struct ptrace_args *uap)
if (error)
return (error);
+ get_mplock();
error = kern_ptrace(p, uap->req, uap->pid, addr, uap->data,
&uap->sysmsg_result);
+ rel_mplock();
if (error)
return (error);
"aio_write", /* 319 = aio_write */
"lio_listio", /* 320 = lio_listio */
"yield", /* 321 = yield */
- "thr_sleep", /* 322 = thr_sleep */
- "thr_wakeup", /* 323 = thr_wakeup */
+ "#322", /* 322 = thr_sleep */
+ "#323", /* 323 = thr_wakeup */
"mlockall", /* 324 = mlockall */
"munlockall", /* 325 = munlockall */
"__getcwd", /* 326 = __getcwd */
; System call name/number master file.
; Processed to created init_sysent.c, syscalls.c and syscall.h.
-; Columns: number [MPSAFE] type nargs namespc name alt{name,tag,rtyp}/comments
+; Columns: number type nargs namespc name alt{name,tag,rtyp}/comments
; number system call number, must be in order
-; MPSAFE optional field, specifies that syscall does not want the
-; BGL grabbed automatically (it is SMP safe).
; type one of STD, OBSOL, UNIMPL, COMPAT, CPT_NOA, LIBCOMPAT,
; NODEF, NOARGS, NOPROTO, NOIMPL
; namespc one of POSIX, BSD, NOHIDE
; alttag name of args struct tag if different from [o]`name'"_args"
; altrtyp return type if not int (bogus - syscalls always return int)
; for UNIMPL/OBSOL, name continues with comments
+;
+; NOTE: All system calls are now called without the MP lock. Those
+; that need the MP lock will acquire it.
; types:
; STD always included
0 STD NOHIDE { int nosys(void); } syscall nosys_args int
1 STD NOHIDE { void exit(int rval); }
2 STD POSIX { int fork(void); }
-3 MPSAFE STD POSIX { ssize_t read(int fd, void *buf, size_t nbyte); }
-4 MPSAFE STD POSIX { ssize_t write(int fd, const void *buf, size_t nbyte); }
+3 STD POSIX { ssize_t read(int fd, void *buf, size_t nbyte); }
+4 STD POSIX { ssize_t write(int fd, const void *buf, size_t nbyte); }
5 STD POSIX { int open(char *path, int flags, int mode); }
; XXX should be { int open(const char *path, int flags, ...); }
; but we're not ready for `const' or varargs.
; XXX man page says `mode_t mode'.
-6 MPSAFE STD POSIX { int close(int fd); }
+6 STD POSIX { int close(int fd); }
7 STD BSD { int wait4(int pid, int *status, int options, \
struct rusage *rusage); } wait4 wait_args int
8 COMPAT BSD { int creat(char *path, int mode); }
; XXX `path' should have type `const char *' but we're not ready for that.
22 STD BSD { int unmount(char *path, int flags); }
23 STD POSIX { int setuid(uid_t uid); }
-24 MPSAFE STD POSIX { uid_t getuid(void); }
-25 MPSAFE STD POSIX { uid_t geteuid(void); }
+24 STD POSIX { uid_t getuid(void); }
+25 STD POSIX { uid_t geteuid(void); }
26 STD BSD { int ptrace(int req, pid_t pid, caddr_t addr, \
int data); }
27 STD BSD { int recvmsg(int s, struct msghdr *msg, int flags); }
38 COMPAT POSIX { int stat(char *path, struct ostat *ub); }
39 STD POSIX { pid_t getppid(void); }
40 COMPAT POSIX { int lstat(char *path, struct ostat *ub); }
-41 MPSAFE STD POSIX { int dup(u_int fd); }
+41 STD POSIX { int dup(u_int fd); }
42 STD POSIX { int pipe(void); }
43 STD POSIX { gid_t getegid(void); }
44 STD BSD { int profil(caddr_t samples, size_t size, \
45 STD BSD { int ktrace(const char *fname, int ops, int facs, \
int pid); }
46 OBSOL NOHIDE freebsd3_sigaction
-47 MPSAFE STD POSIX { gid_t getgid(void); }
+47 STD POSIX { gid_t getgid(void); }
48 OBSOL NOHIDE freebsd3_sigprocmask
; XXX note nonstandard (bogus) calling convention - the libc stub passes
; us the mask, not a pointer to it, and we return the old mask as the
57 STD POSIX { int symlink(char *path, char *link); }
58 STD POSIX { int readlink(char *path, char *buf, int count); }
59 STD POSIX { int execve(char *fname, char **argv, char **envv); }
-60 MPSAFE STD POSIX { int umask(int newmask); } umask umask_args int
+60 STD POSIX { int umask(int newmask); } umask umask_args int
61 STD BSD { int chroot(char *path); }
62 COMPAT POSIX { int fstat(int fd, struct ostat *sb); }
63 COMPAT BSD { int getkerninfo(int op, char *where, size_t *size, \
char *vec); }
79 STD POSIX { int getgroups(u_int gidsetsize, gid_t *gidset); }
80 STD POSIX { int setgroups(u_int gidsetsize, gid_t *gidset); }
-81 MPSAFE STD POSIX { int getpgrp(void); }
+81 STD POSIX { int getpgrp(void); }
82 STD POSIX { int setpgid(int pid, int pgid); }
83 STD BSD { int setitimer(u_int which, struct itimerval *itv, \
struct itimerval *oitv); }
gethostname gethostname_args int
88 COMPAT BSD { int sethostname(char *hostname, u_int len); } \
sethostname sethostname_args int
-89 MPSAFE STD BSD { int getdtablesize(void); }
-90 MPSAFE STD POSIX { int dup2(u_int from, u_int to); }
+89 STD BSD { int getdtablesize(void); }
+90 STD POSIX { int dup2(u_int from, u_int to); }
91 UNIMPL BSD getdopt
-92 MPSAFE STD POSIX { int fcntl(int fd, int&nbs