summaryrefslogtreecommitdiff
path: root/sys/arch/m88k
diff options
context:
space:
mode:
Diffstat (limited to 'sys/arch/m88k')
-rw-r--r--sys/arch/m88k/conf/files.m88k3
-rw-r--r--sys/arch/m88k/m88k/sig_machdep.c232
2 files changed, 234 insertions, 1 deletions
diff --git a/sys/arch/m88k/conf/files.m88k b/sys/arch/m88k/conf/files.m88k
index 11232f62b0d..cb1d10468e7 100644
--- a/sys/arch/m88k/conf/files.m88k
+++ b/sys/arch/m88k/conf/files.m88k
@@ -1,4 +1,4 @@
-# $OpenBSD: files.m88k,v 1.7 2004/08/06 13:23:49 miod Exp $
+# $OpenBSD: files.m88k,v 1.8 2004/09/30 09:20:48 miod Exp $
file arch/m88k/m88k/cmmu.c
file arch/m88k/m88k/db_disasm.c ddb
@@ -12,6 +12,7 @@ file arch/m88k/m88k/m8820x_machdep.c m88100
file arch/m88k/m88k/pmap.c
file arch/m88k/m88k/process.S
file arch/m88k/m88k/process_machdep.c
+file arch/m88k/m88k/sig_machdep.c
file arch/m88k/m88k/subr.S
file arch/m88k/m88k/trap.c
file arch/m88k/m88k/vectors_88100.S m88100
diff --git a/sys/arch/m88k/m88k/sig_machdep.c b/sys/arch/m88k/m88k/sig_machdep.c
new file mode 100644
index 00000000000..c2c3b0457b4
--- /dev/null
+++ b/sys/arch/m88k/m88k/sig_machdep.c
@@ -0,0 +1,232 @@
+/* $OpenBSD: sig_machdep.c,v 1.1 2004/09/30 09:20:48 miod Exp $ */
+/*
+ * Copyright (c) 1998, 1999, 2000, 2001 Steve Murphree, Jr.
+ * Copyright (c) 1996 Nivas Madhur
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by Nivas Madhur.
+ * 4. The name of the author may not be used to endorse or promote products
+ * derived from this software without specific prior written permission
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ */
+/*
+ * Mach Operating System
+ * Copyright (c) 1993-1991 Carnegie Mellon University
+ * Copyright (c) 1991 OMRON Corporation
+ * All Rights Reserved.
+ *
+ * Permission to use, copy, modify and distribute this software and its
+ * documentation is hereby granted, provided that both the copyright
+ * notice and this permission notice appear in all copies of the
+ * software, derivative works or modified versions, and any portions
+ * thereof, and that both notices appear in supporting documentation.
+ *
+ */
+
+#include <sys/param.h>
+#include <sys/systm.h>
+#include <sys/signalvar.h>
+#include <sys/kernel.h>
+#include <sys/proc.h>
+#include <sys/user.h>
+#include <sys/mount.h>
+#include <sys/syscallargs.h>
+#include <sys/errno.h>
+
+#include <machine/reg.h>
+
+#include <uvm/uvm_extern.h>
+
+struct sigstate {
+ int ss_flags; /* which of the following are valid */
+ struct trapframe ss_frame; /* original exception frame */
+};
+
+/*
+ * WARNING: sigcode() in locore.s assumes the layout shown for sf_signo
+ * through sf_handler so... don't screw with them!
+ */
+struct sigframe {
+ int sf_signo; /* signo for handler */
+ siginfo_t *sf_sip;
+ struct sigcontext *sf_scp; /* context ptr for handler */
+ sig_t sf_handler; /* handler addr for u_sigc */
+ struct sigcontext sf_sc; /* actual context */
+ siginfo_t sf_si;
+};
+
+#ifdef DEBUG
+int sigdebug = 0;
+int sigpid = 0;
+#define SDB_FOLLOW 0x01
+#define SDB_KSTACK 0x02
+#endif
+
+/*
+ * Send an interrupt to process.
+ */
+void
+sendsig(sig_t catcher, int sig, int mask, unsigned long code, int type,
+ union sigval val)
+{
+ struct proc *p = curproc;
+ struct trapframe *tf;
+ struct sigacts *psp = p->p_sigacts;
+ struct sigframe *fp;
+ int oonstack, fsize;
+ struct sigframe sf;
+ vaddr_t addr;
+
+ tf = p->p_md.md_tf;
+ oonstack = psp->ps_sigstk.ss_flags & SS_ONSTACK;
+ /*
+ * Allocate and validate space for the signal handler
+ * context. Note that if the stack is in data space, the
+ * call to grow() is a nop, and the copyout()
+ * will fail if the process has not already allocated
+ * the space with a `brk'.
+ */
+ fsize = sizeof(struct sigframe);
+ if ((psp->ps_flags & SAS_ALTSTACK) &&
+ (psp->ps_sigstk.ss_flags & SS_ONSTACK) == 0 &&
+ (psp->ps_sigonstack & sigmask(sig))) {
+ fp = (struct sigframe *)(psp->ps_sigstk.ss_sp +
+ psp->ps_sigstk.ss_size - fsize);
+ psp->ps_sigstk.ss_flags |= SS_ONSTACK;
+ } else
+ fp = (struct sigframe *)(tf->tf_r[31] - fsize);
+
+ /* make sure the frame is aligned on a 8 byte boundary */
+ if (((vaddr_t)fp & 0x07) != 0)
+ fp = (struct sigframe *)((vaddr_t)fp & ~0x07);
+
+ if ((unsigned)fp <= USRSTACK - ctob(p->p_vmspace->vm_ssize))
+ (void)uvm_grow(p, (unsigned)fp);
+
+#ifdef DEBUG
+ if ((sigdebug & SDB_FOLLOW) ||
+ ((sigdebug & SDB_KSTACK) && p->p_pid == sigpid))
+ printf("sendsig(%d): sig %d ssp %x usp %x scp %x\n",
+ p->p_pid, sig, &oonstack, fp, &fp->sf_sc);
+#endif
+ /*
+ * Build the signal context to be used by sigreturn.
+ */
+ sf.sf_signo = sig;
+ sf.sf_scp = &fp->sf_sc;
+ sf.sf_handler = catcher;
+ sf.sf_sc.sc_onstack = oonstack;
+ sf.sf_sc.sc_mask = mask;
+
+ if (psp->ps_siginfo & sigmask(sig)) {
+ sf.sf_sip = &fp->sf_si;
+ initsiginfo(&sf.sf_si, sig, code, type, val);
+ }
+
+ /*
+ * Copy the whole user context into signal context that we
+ * are building.
+ */
+ bcopy((const void *)&tf->tf_regs, (void *)&sf.sf_sc.sc_regs,
+ sizeof(sf.sf_sc.sc_regs));
+
+ if (copyout((caddr_t)&sf, (caddr_t)fp, sizeof sf)) {
+ /*
+ * Process has trashed its stack; give it an illegal
+ * instruction to halt it in its tracks.
+ */
+ sigexit(p, SIGILL);
+ /* NOTREACHED */
+ }
+ /*
+ * Build the argument list for the signal handler.
+ * Signal trampoline code is at base of user stack.
+ */
+ addr = p->p_sigcode;
+ if (cputyp != CPU_88110) {
+#ifdef M88100
+ /* mc88100 */
+ tf->tf_snip = (addr & ~3) | NIP_V;
+ tf->tf_sfip = (tf->tf_snip + 4) | FIP_V;
+#endif
+ } else {
+#ifdef M88110
+ /* mc88110 */
+ tf->tf_exip = (addr & ~3);
+ tf->tf_enip = (tf->tf_exip + 4);
+#endif
+ }
+ tf->tf_r[31] = (unsigned)fp;
+#ifdef DEBUG
+ if ((sigdebug & SDB_FOLLOW) ||
+ ((sigdebug & SDB_KSTACK) && p->p_pid == sigpid))
+ printf("sendsig(%d): sig %d returns\n", p->p_pid, sig);
+#endif
+}
+
+/*
+ * System call to cleanup state after a signal has been taken. Reset signal
+ * mask and stack state from context left by sendsig (above). Return to
+ * previous pc and psl as specified by context left by sendsig. Check
+ * carefully to make sure that the user has not modified the psl to gain
+ * improper privileges or to cause a machine fault.
+ */
+
+/* ARGSUSED */
+int
+sys_sigreturn(struct proc *p, void *v, register_t *retval)
+{
+ struct sys_sigreturn_args /* {
+ syscallarg(struct sigcontext *) sigcntxp;
+ } */ *uap = v;
+ struct sigcontext *scp;
+ struct trapframe *tf;
+ struct sigcontext ksc;
+
+ scp = (struct sigcontext *)SCARG(uap, sigcntxp);
+#ifdef DEBUG
+ if (sigdebug & SDB_FOLLOW)
+ printf("sigreturn: pid %d, scp %x\n", p->p_pid, scp);
+#endif
+ if (((vaddr_t)scp & 3) != 0 ||
+ copyin((caddr_t)scp, (caddr_t)&ksc, sizeof(struct sigcontext)))
+ return (EINVAL);
+
+ tf = p->p_md.md_tf;
+ scp = &ksc;
+
+ bcopy((const void *)&scp->sc_regs, (caddr_t)&tf->tf_regs,
+ sizeof(scp->sc_regs));
+
+ /*
+ * Restore the user supplied information
+ */
+ if (scp->sc_onstack & SS_ONSTACK)
+ p->p_sigacts->ps_sigstk.ss_flags |= SS_ONSTACK;
+ else
+ p->p_sigacts->ps_sigstk.ss_flags &= ~SS_ONSTACK;
+ p->p_sigmask = scp->sc_mask & ~sigcantmask;
+
+ return (EJUSTRETURN);
+}