aboutsummaryrefslogtreecommitdiff
path: root/sys/ia64
diff options
context:
space:
mode:
authorDavid Xu <davidxu@FreeBSD.org>2005-10-14 12:43:47 +0000
committerDavid Xu <davidxu@FreeBSD.org>2005-10-14 12:43:47 +0000
commit9104847f216771dfda5d78a6dd4974882f1a55cd (patch)
tree95d82b1a11b0c187223f8ac12f020b19901fa750 /sys/ia64
parentde90a634cba8adb2ba64538ba6d99c72b5794507 (diff)
downloadsrc-9104847f216771dfda5d78a6dd4974882f1a55cd.tar.gz
src-9104847f216771dfda5d78a6dd4974882f1a55cd.zip
1. Change prototype of trapsignal and sendsig to use ksiginfo_t *, most
changes in MD code are trivial, before this change, trapsignal and sendsig use discrete parameters, now they uses member fields of ksiginfo_t structure. For sendsig, this change allows us to pass POSIX realtime signal value to user code. 2. Remove cpu_thread_siginfo, it is no longer needed because we now always generate ksiginfo_t data and feed it to libpthread. 3. Add p_sigqueue to proc structure to hold shared signals which were blocked by all threads in the proc. 4. Add td_sigqueue to thread structure to hold all signals delivered to thread. 5. i386 and amd64 now return POSIX standard si_code, other arches will be fixed. 6. In this sigqueue implementation, pending signal set is kept as before, an extra siginfo list holds additional siginfo_t data for signals. kernel code uses psignal() still behavior as before, it won't be failed even under memory pressure, only exception is when deleting a signal, we should call sigqueue_delete to remove signal from sigqueue but not SIGDELSET. Current there is no kernel code will deliver a signal with additional data, so kernel should be as stable as before, a ksiginfo can carry more information, for example, allow signal to be delivered but throw away siginfo data if memory is not enough. SIGKILL and SIGSTOP have fast path in sigqueue_add, because they can not be caught or masked. The sigqueue() syscall allows user code to queue a signal to target process, if resource is unavailable, EAGAIN will be returned as specification said. Just before thread exits, signal queue memory will be freed by sigqueue_flush. Current, all signals are allowed to be queued, not only realtime signals. Earlier patch reviewed by: jhb, deischen Tested on: i386, amd64
Notes
Notes: svn path=/head/; revision=151316
Diffstat (limited to 'sys/ia64')
-rw-r--r--sys/ia64/ia32/ia32_signal.c4
-rw-r--r--sys/ia64/ia32/ia32_trap.c14
-rw-r--r--sys/ia64/ia64/machdep.c31
-rw-r--r--sys/ia64/ia64/trap.c6
4 files changed, 29 insertions, 26 deletions
diff --git a/sys/ia64/ia32/ia32_signal.c b/sys/ia64/ia32/ia32_signal.c
index 6725cb33f912..b5b788a590c0 100644
--- a/sys/ia64/ia32/ia32_signal.c
+++ b/sys/ia64/ia32/ia32_signal.c
@@ -98,9 +98,9 @@ int sz_ia32_sigcode = sizeof(ia32_sigcode);
* sendsig() means that at least untrapped signals will work.
*/
void
-ia32_sendsig(sig_t catcher, int sig, sigset_t *mask, u_long code)
+ia32_sendsig(sig_t catcher, ksiginfo_t *ksi, sigset_t *mask)
{
- sendsig(catcher, sig, mask, code);
+ sendsig(catcher, ksi, mask);
}
#ifdef COMPAT_FREEBSD4
diff --git a/sys/ia64/ia32/ia32_trap.c b/sys/ia64/ia32/ia32_trap.c
index 58a805f60079..d93722ed522f 100644
--- a/sys/ia64/ia32/ia32_trap.c
+++ b/sys/ia64/ia32/ia32_trap.c
@@ -61,6 +61,7 @@ ia32_syscall(struct trapframe *tf)
register_t eflags;
u_int code;
int error, i, narg;
+ ksiginfo_t ksi;
PCPU_LAZY_INC(cnt.v_syscall);
@@ -168,7 +169,11 @@ ia32_syscall(struct trapframe *tf)
*/
if ((eflags & PSL_T) && !(eflags & PSL_VM)) {
ia64_set_eflag(ia64_get_eflag() & ~PSL_T);
- trapsignal(td, SIGTRAP, 0);
+ ksiginfo_init_trap(&ksi);
+ ksi.ksi_signo = SIGTRAP;
+ ksi.ksi_code = TRAP_TRACE;
+ ksi.ksi_addr = (void *)tf->tf_special.iip;
+ trapsignal(td, &ksi);
}
#ifdef KTRACE
@@ -201,6 +206,7 @@ ia32_trap(int vector, struct trapframe *tf)
uint64_t ucode;
int sig;
u_int sticks;
+ ksiginfo_t ksi;
KASSERT(TRAPF_USERMODE(tf), ("%s: In kernel mode???", __func__));
@@ -284,7 +290,11 @@ ia32_trap(int vector, struct trapframe *tf)
KASSERT(sig != 0, ("%s: signal not set", __func__));
- trapsignal(td, sig, ucode);
+ ksiginfo_init_trap(&ksi);
+ ksi.ksi_signo = sig;
+ ksi.ksi_code = (int)ucode; /* XXX */
+ /* ksi.ksi_addr */
+ trapsignal(td, &ksi);
out:
userret(td, tf, sticks);
diff --git a/sys/ia64/ia64/machdep.c b/sys/ia64/ia64/machdep.c
index 2baf57dd006c..19c4f83a3dcb 100644
--- a/sys/ia64/ia64/machdep.c
+++ b/sys/ia64/ia64/machdep.c
@@ -878,7 +878,7 @@ DELAY(int n)
* Send an interrupt (signal) to a process.
*/
void
-sendsig(sig_t catcher, int sig, sigset_t *mask, u_long code)
+sendsig(sig_t catcher, ksiginfo_t *ksi, sigset_t *mask)
{
struct proc *p;
struct thread *td;
@@ -887,10 +887,14 @@ sendsig(sig_t catcher, int sig, sigset_t *mask, u_long code)
struct sigframe sf, *sfp;
u_int64_t sbs, sp;
int oonstack;
+ int sig;
+ u_long code;
td = curthread;
p = td->td_proc;
PROC_LOCK_ASSERT(p, MA_OWNED);
+ sig = ksi->ksi_signo;
+ code = ksi->ksi_code;
psp = p->p_sigacts;
mtx_assert(&psp->ps_mtx, MA_OWNED);
tf = td->td_frame;
@@ -926,8 +930,12 @@ sendsig(sig_t catcher, int sig, sigset_t *mask, u_long code)
/* Fill in the siginfo structure for POSIX handlers. */
if (SIGISMEMBER(psp->ps_siginfo, sig)) {
+ sf.sf_si = ksi->ksi_info;
sf.sf_si.si_signo = sig;
- sf.sf_si.si_code = code;
+ /*
+ * XXX this shouldn't be here after code in trap.c
+ * is fixed
+ */
sf.sf_si.si_addr = (void*)tf->tf_special.ifa;
code = (u_int64_t)&sfp->sf_si;
}
@@ -979,25 +987,6 @@ sendsig(sig_t catcher, int sig, sigset_t *mask, u_long code)
}
/*
- * Build siginfo_t for SA thread
- */
-void
-cpu_thread_siginfo(int sig, u_long code, siginfo_t *si)
-{
- struct proc *p;
- struct thread *td;
-
- td = curthread;
- p = td->td_proc;
- PROC_LOCK_ASSERT(p, MA_OWNED);
-
- bzero(si, sizeof(*si));
- si->si_signo = sig;
- si->si_code = code;
- /* XXXKSE fill other fields */
-}
-
-/*
* System call to cleanup state after a signal
* has been taken. Reset signal mask and
* stack state from context left by sendsig (above).
diff --git a/sys/ia64/ia64/trap.c b/sys/ia64/ia64/trap.c
index d68482413912..432ac69799d3 100644
--- a/sys/ia64/ia64/trap.c
+++ b/sys/ia64/ia64/trap.c
@@ -361,6 +361,7 @@ trap(int vector, struct trapframe *tf)
uint64_t ucode;
int error, sig, user;
u_int sticks;
+ ksiginfo_t ksi;
user = TRAPF_USERMODE(tf) ? 1 : 0;
@@ -869,7 +870,10 @@ trap(int vector, struct trapframe *tf)
if (print_usertrap)
printtrap(vector, tf, 1, user);
- trapsignal(td, sig, ucode);
+ ksiginfo_init(&ksi);
+ ksi.ksi_signo = sig;
+ ksi.ksi_code = ucode;
+ trapsignal(td, &ksi);
out:
if (user) {