use netbsd <sys/signal.h> and sigset_t

. create signals-related struct message type to store sigset_t
	  directly
	. create notify-specific message types, so the generic NOTIFY_ARG
	  doesn't exist anymore
	. various related test expansions, improvements, fixes
	. add a few error-checks to sigismember() calls
	. rename kernel call specific signals fields to SYS_*

Change-Id: I53c18999b5eaf0cfa0cb25f5330bee9e7ad2b478
This commit is contained in:
Ben Gras
2013-10-22 17:08:15 +02:00
committed by Lionel Sambuc
parent 6c3dfa5f3c
commit 8ccb12bb5a
48 changed files with 407 additions and 291 deletions

View File

@@ -34,6 +34,7 @@
#include <stddef.h>
#include <signal.h>
#include <assert.h>
#include <string.h>
#include "kernel/kernel.h"
#include "vm.h"
@@ -98,16 +99,19 @@ static void set_idle_name(char * name, int n)
#define PICK_HIGHERONLY 2
#define BuildNotifyMessage(m_ptr, src, dst_ptr) \
memset((m_ptr), 0, sizeof(*(m_ptr))); \
(m_ptr)->m_type = NOTIFY_MESSAGE; \
(m_ptr)->NOTIFY_TIMESTAMP = get_monotonic(); \
switch (src) { \
case HARDWARE: \
(m_ptr)->NOTIFY_ARG = priv(dst_ptr)->s_int_pending; \
(m_ptr)->NOTIFY_INTMASK = priv(dst_ptr)->s_int_pending; \
priv(dst_ptr)->s_int_pending = 0; \
break; \
case SYSTEM: \
(m_ptr)->NOTIFY_ARG = priv(dst_ptr)->s_sig_pending; \
priv(dst_ptr)->s_sig_pending = 0; \
memcpy(&(m_ptr)->NOTIFY_SIGSET, \
&priv(dst_ptr)->s_sig_pending, \
sizeof(sigset_t)); \
sigemptyset(&priv(dst_ptr)->s_sig_pending); \
break; \
}

View File

@@ -408,6 +408,7 @@ int sig_nr; /* signal to be sent */
register struct proc *rp, *sig_mgr_rp;
endpoint_t sig_mgr;
int sig_mgr_proc_nr;
int s;
/* Lookup signal manager. */
rp = proc_addr(proc_nr);
@@ -438,8 +439,10 @@ int sig_nr; /* signal to be sent */
return;
}
if((s = sigismember(&rp->p_pending, sig_nr)) < 0)
panic("sigismember failed");
/* Check if the signal is already pending. Process it otherwise. */
if (! sigismember(&rp->p_pending, sig_nr)) {
if (!s) {
sigaddset(&rp->p_pending, sig_nr);
increase_proc_signals(rp);
if (! (RTS_ISSET(rp, RTS_SIGNALED))) { /* other pending */

View File

@@ -24,7 +24,7 @@ int do_endksig(struct proc * caller, message * m_ptr)
/* Get process pointer and verify that it had signals pending. If the
* process is already dead its flags will be reset.
*/
if(!isokendpt(m_ptr->SIG_ENDPT, &proc_nr))
if(!isokendpt(m_ptr->SYS_SIG_ENDPT, &proc_nr))
return EINVAL;
rp = proc_addr(proc_nr);

View File

@@ -2,8 +2,8 @@
* m_type: SYS_GETKSIG
*
* The parameters for this kernel call are:
* m2_i1: SIG_ENDPT # process with pending signals
* m2_l1: SIG_MAP # bit map with pending signals
* m2_i1: SYS_SIG_ENDPT # process with pending signals
* m2_l1: SYS_SIG_MAP # bit map with pending signals
*/
#include "kernel/system.h"
@@ -28,8 +28,8 @@ int do_getksig(struct proc * caller, message * m_ptr)
if (RTS_ISSET(rp, RTS_SIGNALED)) {
if (caller->p_endpoint != priv(rp)->s_sig_mgr) continue;
/* store signaled process' endpoint */
m_ptr->SIG_ENDPT = rp->p_endpoint;
m_ptr->SIG_MAP = rp->p_pending; /* pending signals map */
m_ptr->SYS_SIG_ENDPT = rp->p_endpoint;
m_ptr->SYS_SIG_MAP = rp->p_pending; /* pending signals map */
(void) sigemptyset(&rp->p_pending); /* clear map in the kernel */
RTS_UNSET(rp, RTS_SIGNALED); /* blocked by SIG_PENDING */
return(OK);
@@ -37,7 +37,7 @@ int do_getksig(struct proc * caller, message * m_ptr)
}
/* No process with pending signals was found. */
m_ptr->SIG_ENDPT = NONE;
m_ptr->SYS_SIG_ENDPT = NONE;
return(OK);
}
#endif /* USE_GETKSIG */

View File

@@ -2,8 +2,8 @@
* m_type: SYS_KILL
*
* The parameters for this kernel call are:
* m2_i1: SIG_ENDPT # process to signal/ pending
* m2_i2: SIG_NUMBER # signal number to send to process
* m2_i1: SYS_SIG_ENDPT # process to signal/ pending
* m2_i2: SYS_SIG_NUMBER # signal number to send to process
*/
#include "kernel/system.h"
@@ -23,9 +23,9 @@ int do_kill(struct proc * caller, message * m_ptr)
* translated into an IPC message for system services.
*/
proc_nr_t proc_nr, proc_nr_e;
int sig_nr = m_ptr->SIG_NUMBER;
int sig_nr = m_ptr->SYS_SIG_NUMBER;
proc_nr_e= (proc_nr_t) m_ptr->SIG_ENDPT;
proc_nr_e= (proc_nr_t) m_ptr->SYS_SIG_ENDPT;
if (!isokendpt(proc_nr_e, &proc_nr)) return(EINVAL);
if (sig_nr >= _NSIG) return(EINVAL);

View File

@@ -25,12 +25,12 @@ int do_sigreturn(struct proc * caller, message * m_ptr)
register struct proc *rp;
int proc_nr, r;
if (! isokendpt(m_ptr->SIG_ENDPT, &proc_nr)) return(EINVAL);
if (! isokendpt(m_ptr->SYS_SIG_ENDPT, &proc_nr)) return(EINVAL);
if (iskerneln(proc_nr)) return(EPERM);
rp = proc_addr(proc_nr);
/* Copy in the sigcontext structure. */
if((r=data_copy(m_ptr->SIG_ENDPT, (vir_bytes) m_ptr->SIG_CTXT_PTR,
if((r=data_copy(m_ptr->SYS_SIG_ENDPT, (vir_bytes) m_ptr->SYS_SIG_CTXT_PTR,
KERNEL, (vir_bytes) &sc, sizeof(struct sigcontext))) != OK)
return r;

View File

@@ -2,9 +2,9 @@
* m_type: SYS_SIGSEND
*
* The parameters for this kernel call are:
* m2_i1: SIG_ENDPT # process to call signal handler
* m2_p1: SIG_CTXT_PTR # pointer to sigcontext structure
* m2_i3: SIG_FLAGS # flags for S_SIGRETURN call
* m2_i1: SYS_SIG_ENDPT # process to call signal handler
* m2_p1: SYS_SIG_CTXT_PTR # pointer to sigcontext structure
* m2_i3: SYS_SIG_FLAGS # flags for S_SIGRETURN call
*
*/
@@ -27,13 +27,13 @@ int do_sigsend(struct proc * caller, message * m_ptr)
struct sigframe fr, *frp;
int proc_nr, r;
if (!isokendpt(m_ptr->SIG_ENDPT, &proc_nr)) return(EINVAL);
if (!isokendpt(m_ptr->SYS_SIG_ENDPT, &proc_nr)) return(EINVAL);
if (iskerneln(proc_nr)) return(EPERM);
rp = proc_addr(proc_nr);
/* Get the sigmsg structure into our address space. */
if((r=data_copy_vmcheck(caller, caller->p_endpoint,
(vir_bytes) m_ptr->SIG_CTXT_PTR, KERNEL, (vir_bytes) &smsg,
(vir_bytes) m_ptr->SYS_SIG_CTXT_PTR, KERNEL, (vir_bytes) &smsg,
(phys_bytes) sizeof(struct sigmsg))) != OK)
return r;
@@ -64,7 +64,7 @@ int do_sigsend(struct proc * caller, message * m_ptr)
sc.sc_flags = rp->p_misc_flags & MF_FPU_INITIALIZED;
/* Copy the sigcontext structure to the user's stack. */
if((r=data_copy_vmcheck(caller, KERNEL, (vir_bytes) &sc, m_ptr->SIG_ENDPT,
if((r=data_copy_vmcheck(caller, KERNEL, (vir_bytes) &sc, m_ptr->SYS_SIG_ENDPT,
(vir_bytes) scp, (vir_bytes) sizeof(struct sigcontext))) != OK)
return r;
@@ -97,7 +97,7 @@ int do_sigsend(struct proc * caller, message * m_ptr)
/* Copy the sigframe structure to the user's stack. */
if((r=data_copy_vmcheck(caller, KERNEL, (vir_bytes) &fr,
m_ptr->SIG_ENDPT, (vir_bytes) frp,
m_ptr->SYS_SIG_ENDPT, (vir_bytes) frp,
(vir_bytes) sizeof(struct sigframe))) != OK)
return r;