Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys Reworked IRIX signal delivery so that ucontext is used i...
details: https://anonhg.NetBSD.org/src/rev/4aba03ab7e14
branches: trunk
changeset: 525532:4aba03ab7e14
user: manu <manu%NetBSD.org@localhost>
date: Fri Apr 12 18:44:57 2002 +0000
description:
Reworked IRIX signal delivery so that ucontext is used instead of sigcontext
when SA_SIGINFO is used. The IRIX process will hence find the expected
information using the third argument of the signal handler.
We do not provide code and siginfo yet.
diffstat:
sys/arch/mips/mips/locore.S | 13 +-
sys/compat/irix/irix_signal.c | 368 ++++++++++++++++++++++++++++--------
sys/compat/irix/irix_signal.h | 27 +-
sys/compat/irix/irix_syscall.h | 6 +-
sys/compat/irix/irix_syscallargs.h | 8 +-
sys/compat/irix/irix_syscalls.c | 6 +-
sys/compat/irix/irix_sysent.c | 8 +-
sys/compat/irix/syscalls.master | 5 +-
8 files changed, 329 insertions(+), 112 deletions(-)
diffs (truncated from 707 to 300 lines):
diff -r 08551fb82e4c -r 4aba03ab7e14 sys/arch/mips/mips/locore.S
--- a/sys/arch/mips/mips/locore.S Fri Apr 12 18:02:04 2002 +0000
+++ b/sys/arch/mips/mips/locore.S Fri Apr 12 18:44:57 2002 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: locore.S,v 1.135 2002/04/03 13:57:47 simonb Exp $ */
+/* $NetBSD: locore.S,v 1.136 2002/04/12 18:44:57 manu Exp $ */
/*
* Copyright (c) 1992, 1993
@@ -205,9 +205,14 @@
#ifdef COMPAT_IRIX
#define SYSCALL_SHIFT 1000 # 1000 shift as in irix_syscall.c
LEAF_NOPROFILE(irix_sigcode)
- move a0, sp
- li v0, IRIX_SYS_sigreturn + SYSCALL_SHIFT # sigreturn(sf)
- syscall
+# lw t1,32(sp)
+# lw t0,28(sp)
+# sw t1,0(t0)
+ lw a0,40(sp)
+ lw a1,44(sp)
+ lw a2,36(sp)
+ li v0, IRIX_SYS_sigreturn + SYSCALL_SHIFT
+ syscall # sigreturn(scp, ucp, sig)
break 0 # just in case sigreturn fails
END(irix_sigcode)
XLEAF(irix_esigcode)
diff -r 08551fb82e4c -r 4aba03ab7e14 sys/compat/irix/irix_signal.c
--- a/sys/compat/irix/irix_signal.c Fri Apr 12 18:02:04 2002 +0000
+++ b/sys/compat/irix/irix_signal.c Fri Apr 12 18:44:57 2002 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: irix_signal.c,v 1.11 2002/04/01 15:45:16 manu Exp $ */
+/* $NetBSD: irix_signal.c,v 1.12 2002/04/12 18:44:58 manu Exp $ */
/*-
* Copyright (c) 1994, 2001-2002 The NetBSD Foundation, Inc.
@@ -37,7 +37,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: irix_signal.c,v 1.11 2002/04/01 15:45:16 manu Exp $");
+__KERNEL_RCSID(0, "$NetBSD: irix_signal.c,v 1.12 2002/04/12 18:44:58 manu Exp $");
#include <sys/types.h>
#include <sys/signal.h>
@@ -70,6 +70,12 @@
extern const int svr4_to_native_signo[];
static int irix_setinfo __P((struct proc *, int, irix_irix5_siginfo_t *));
+static void irix_set_ucontext __P((struct irix_ucontext*, sigset_t *,
+ int, struct proc *));
+static void irix_set_sigcontext __P((struct irix_sigcontext*, sigset_t *,
+ int, struct proc *));
+static void irix_get_ucontext __P((struct irix_ucontext*, struct proc *));
+static void irix_get_sigcontext __P((struct irix_sigcontext*, struct proc *));
#define irix_sigmask(n) (1 << (((n) - 1) & 31))
#define irix_sigword(n) (((n) - 1) >> 5)
@@ -80,7 +86,7 @@
/*
* This is ripped from svr4_setinfo. See irix_sys_waitsys...
*/
-int
+static int
irix_setinfo(p, st, s)
struct proc *p;
int st;
@@ -168,24 +174,28 @@
}
void
-irix_sendsig(catcher, sig, mask, code) /* XXX Check me */
+irix_sendsig(catcher, sig, mask, code)
sig_t catcher;
int sig;
sigset_t *mask;
u_long code;
{
struct proc *p = curproc;
- struct irix_sigcontext *fp;
+ void *fp;
+ void *sp;
struct frame *f;
- int i,onstack;
- struct irix_sigcontext sc;
+ int onstack;
+ int error;
+ struct irix_sigframe sf;
+ f = (struct frame *)p->p_md.md_regs;
#ifdef DEBUG_IRIX
printf("irix_sendsig()\n");
printf("catcher = %p, sig = %d, code = 0x%lx\n",
(void *)catcher, sig, code);
+ printf("irix_sendsig(): starting [PC=%p SP=%p SR=0x%08lx]\n",
+ (void *)f->f_regs[PC], (void *)f->f_regs[SP], f->f_regs[SR]);
#endif /* DEBUG_IRIX */
- f = (struct frame *)p->p_md.md_regs;
/*
* Do we need to jump onto the signal stack?
@@ -201,60 +211,56 @@
* Allocate space for the signal handler context.
*/
if (onstack)
- fp = (struct irix_sigcontext *)
- ((caddr_t)p->p_sigctx.ps_sigstk.ss_sp
+ sp = (void *)((caddr_t)p->p_sigctx.ps_sigstk.ss_sp
+ p->p_sigctx.ps_sigstk.ss_size);
else
/* cast for _MIPS_BSD_API == _MIPS_BSD_API_LP32_64CLEAN case */
- fp = (struct irix_sigcontext *)(u_int32_t)f->f_regs[SP];
+ sp = (void *)(u_int32_t)f->f_regs[SP];
+
+ /*
+ * Build the signal frame
+ */
+ bzero(&sf, sizeof(sf));
+ if (SIGACTION(p, sig).sa_flags & SA_SIGINFO)
+ irix_set_ucontext(&sf.isf_ctx.iuc, mask, code, p);
+ else
+ irix_set_sigcontext(&sf.isf_ctx.isc, mask, code, p);
+
+ sf.isf_signo = native_to_svr4_signo[sig];
/*
- * Build stack frame for signal trampoline.
+ * XXX On, IRIX, the sigframe holds a pointer to
+ * errno in userspace. This is used by the signal
+ * trampoline. No idea how to emulate this for now...
*/
- memset(&sc, 0, sizeof sc);
+ /* sf.isf_errno = 0; */
- native_to_irix_sigset(mask, &sc.isc_sigset);
- for (i = 1; i < 32; i++) { /* save gpr1 - gpr31 */
- sc.isc_regs[i] = f->f_regs[i];
- }
- sc.isc_regs[0] = 0;
- sc.isc_fp_rounded_result = 0;
- sc.isc_regmask = ~0x1UL;
- sc.isc_mdhi = f->f_regs[MULHI];
- sc.isc_mdlo = f->f_regs[MULLO];
- sc.isc_pc = f->f_regs[PC];
-
- /*
- * Save the floating-pointstate, if necessary, then copy it.
+ /*
+ * Compute the new stack address after copying sigframe (hold by sp),
+ * and the address of the sigcontext/ucontext (hold by fp)
*/
-#ifndef SOFTFLOAT
- sc.isc_ownedfp = p->p_md.md_flags & MDP_FPUSED;
- if (sc.isc_ownedfp) {
- /* if FPU has current state, save it first */
- if (p == fpcurproc)
- savefpregs(p);
- (void)memcpy(&sc.isc_fpregs, &p->p_addr->u_pcb.pcb_fpregs,
- sizeof(sc.isc_fpregs));
- sc.isc_fpc_csr = p->p_addr->u_pcb.pcb_fpregs.r_regs[32];
+ sp = (void *)((unsigned long)sp - sizeof(sf));
+ sp = (void *)((unsigned long)sp & ~0xfUL); /* 16 bytes alignement */
+ fp = (void *)((unsigned long)sp + sizeof(sf) - sizeof(sf.isf_ctx));
+
+
+ /*
+ * If SA_SIGINFO is used, then ucp is used, and scp = NULL,
+ * if it is not used, then scp is used, and ucp = scp
+ */
+ if (SIGACTION(p, sig).sa_flags & SA_SIGINFO) {
+ sf.isf_ucp = (struct irix_ucontext *)fp;
+ sf.isf_scp = NULL;
+ } else {
+ sf.isf_ucp = (struct irix_ucontext *)fp;
+ sf.isf_scp = (struct irix_sigcontext *)fp;
}
-#else
- (void)memcpy(&sc.isc_fpregs, &p->p_addr->u_pcb.pcb_fpregs,
- sizeof(sc.isc_fpregs));
-#endif
- /*
- * Save signal stack
- */
- sc.isc_ssflags =
- (p->p_sigctx.ps_sigstk.ss_flags & SS_ONSTACK) ? IRIX_SS_ONSTACK : 0;
/*
* Install the sigframe onto the stack
*/
- fp = (struct irix_sigcontext *)((unsigned long)fp
- - sizeof(struct irix_sigcontext));
- fp = (struct irix_sigcontext *)((unsigned long)fp
- & ~0xfUL); /* 16 bytes alignement */
- if (copyout(&sc, fp, sizeof(sc)) != 0) {
+ error = copyout(&sf, sp, sizeof(sf));
+ if (error != 0) {
/*
* Process has trashed its stack; give it an illegal
* instruction to halt it in its tracks.
@@ -266,22 +272,29 @@
/* NOTREACHED */
}
- /* Set up the registers to return to sigcode. */
- f->f_regs[A0] = native_to_svr4_signo[sig];
- f->f_regs[A1] = 0;
- f->f_regs[A2] = (unsigned long)fp;
+ /*
+ * Set up signal handler arguments.
+ */
+ f->f_regs[A0] = native_to_svr4_signo[sig]; /* signo/signo */
+ f->f_regs[A1] = 0; /* code/siginfo */
+ f->f_regs[A2] = (unsigned long)fp; /* sigcontext/ucontext */
#ifdef DEBUG_IRIX
- printf("sigcontext is at %p\n", fp);
+ printf("sigcontext is at %p, stack pointer at %p\n", fp, sp);
#endif /* DEBUG_IRIX */
+ /*
+ * Set up the registers to return to sigcode.
+ */
f->f_regs[RA] = (unsigned long)p->p_sigctx.ps_sigcode;
- f->f_regs[SP] = (unsigned long)fp;
+ f->f_regs[SP] = (unsigned long)sp;
f->f_regs[T9] = (unsigned long)catcher;
f->f_regs[A3] = (unsigned long)catcher;
f->f_regs[PC] = (unsigned long)catcher;
- /* Remember that we're now on the signal stack. */
+ /*
+ * Remember that we're now on the signal stack.
+ */
if (onstack)
p->p_sigctx.ps_sigstk.ss_flags |= SS_ONSTACK;
@@ -291,6 +304,109 @@
return;
}
+static void
+irix_set_sigcontext (scp, mask, code, p)
+ struct irix_sigcontext *scp;
+ sigset_t *mask;
+ int code;
+ struct proc *p;
+{
+ int i;
+ struct frame *f;
+
+#ifdef DEBUG_IRIX
+ printf("irix_set_sigcontext()\n");
+#endif
+ f = (struct frame *)p->p_md.md_regs;
+ /*
+ * Build stack frame for signal trampoline.
+ */
+ native_to_irix_sigset(mask, &scp->isc_sigset);
+ for (i = 1; i < 32; i++) { /* save gpr1 - gpr31 */
+ scp->isc_regs[i] = f->f_regs[i];
+ }
+ scp->isc_regs[0] = 0;
+ scp->isc_fp_rounded_result = 0;
+ scp->isc_regmask = ~0x1UL;
+ scp->isc_mdhi = f->f_regs[MULHI];
+ scp->isc_mdlo = f->f_regs[MULLO];
+ scp->isc_pc = f->f_regs[PC];
+
+ /*
+ * Save the floating-pointstate, if necessary, then copy it.
+ */
+#ifndef SOFTFLOAT
+ scp->isc_ownedfp = p->p_md.md_flags & MDP_FPUSED;
+ if (scp->isc_ownedfp) {
+ /* if FPU has current state, save it first */
+ if (p == fpcurproc)
+ savefpregs(p);
+ (void)memcpy(&scp->isc_fpregs, &p->p_addr->u_pcb.pcb_fpregs,
+ sizeof(scp->isc_fpregs));
+ scp->isc_fpc_csr = p->p_addr->u_pcb.pcb_fpregs.r_regs[32];
+ }
+#else
+ (void)memcpy(&scp->isc_fpregs, &p->p_addr->u_pcb.pcb_fpregs,
+ sizeof(scp->isc_fpregs));
+#endif
+ /*
+ * Save signal stack
+ */
+ scp->isc_ssflags =
+ (p->p_sigctx.ps_sigstk.ss_flags & SS_ONSTACK) ? IRIX_SS_ONSTACK : 0;
+
+ return;
+}
+
+void
+irix_set_ucontext(ucp, mask, code, p)
+ struct irix_ucontext *ucp;
+ sigset_t *mask;
+ int code;
+ struct proc *p;
Home |
Main Index |
Thread Index |
Old Index