- if ((new_task == TASK_NULL) || (thr_act == (thread_t)NULL) || is_kerneltask(new_task))
- return;
-
-
- uth = get_bsdthread_info(thr_act);
- signal_lock(p);
-
- /*
- * proc is traced, always give parent a chance.
- */
- action = SIG_DFL;
-
- if (p->p_nice > NZERO && action == SIG_DFL && (prop & SA_KILL) &&
- (p->p_flag & P_TRACED) == 0)
- p->p_nice = NZERO;
-
- if (prop & SA_CONT) {
- p->p_siglist &= ~stopsigmask;
- uth->uu_siglist &= ~stopsigmask;
- }
-
- if (prop & SA_STOP) {
- /*
- * If sending a tty stop signal to a member of an orphaned
- * process group, discard the signal here if the action
- * is default; don't stop the process below if sleeping,
- * and don't clear any pending SIGCONT.
- */
- if (prop & SA_TTYSTOP && p->p_pgrp->pg_jobc == 0 &&
- action == SIG_DFL)
- goto psigout;
- uth->uu_siglist &= ~contsigmask;
- p->p_siglist &= ~contsigmask;
- }
- uth->uu_siglist |= mask;
- p->p_siglist |= mask; /* just for lame ones looking here */
-
- /* Deliver signal to the activation passed in */
- act_set_astbsd(thr_act);
-
- /*
- * SIGKILL priority twiddling moved here from above because
- * it needs sig_thread. Could merge it into large switch
- * below if we didn't care about priority for tracing
- * as SIGKILL's action is always SIG_DFL.
- */
- if ((signum == SIGKILL) && (p->p_nice > NZERO)) {
- p->p_nice = NZERO;
- }
-
- /*
- * This Process is traced - wake it up (if not already
- * stopped) so that it can discover the signal in
- * issig() and stop for the parent.
- */
- if (p->p_flag & P_TRACED) {
- if (p->p_stat != SSTOP)
- goto run;
- else
- goto psigout;
- }
-run:
- /*
- * If we're being traced (possibly because someone attached us
- * while we were stopped), check for a signal from the debugger.
- */
- if (p->p_stat == SSTOP) {
- if ((p->p_flag & P_TRACED) != 0 && p->p_xstat != 0) {
- uth->uu_siglist |= sigmask(p->p_xstat);
- p->p_siglist |= mask; /* just for lame ones looking here */
- }
- }
-
- /*
- * setrunnable(p) in BSD
- */
- p->p_stat = SRUN;
-
-psigout:
- signal_unlock(p);
-}
-
-static thread_t
-get_signalthread(struct proc *p, int signum)
-{
- struct uthread *uth;
- thread_t thr_act;
- sigset_t mask = sigmask(signum);
- thread_t sig_thread_act;
- struct task * sig_task = p->task;
- kern_return_t kret;
-
- if ((p->p_flag & P_INVFORK) && p->p_vforkact) {
- sig_thread_act = p->p_vforkact;
- kret = check_actforsig(sig_task, sig_thread_act, 1);
- if (kret == KERN_SUCCESS)
- return(sig_thread_act);
- else
- return(THREAD_NULL);
- }
-
- TAILQ_FOREACH(uth, &p->p_uthlist, uu_list) {
- if(((uth->uu_flag & UT_NO_SIGMASK)== 0) &&
- (((uth->uu_sigmask & mask) == 0) || (uth->uu_sigwait & mask))) {
- if (check_actforsig(p->task, uth->uu_act, 1) == KERN_SUCCESS)
- return(uth->uu_act);
- }
- }
- if (get_signalact(p->task, &thr_act, 1) == KERN_SUCCESS) {
- return(thr_act);
- }
-
- return(THREAD_NULL);
-}
-
-/*
- * Send the signal to the process. If the signal has an action, the action
- * is usually performed by the target process rather than the caller; we add
- * the signal to the set of pending signals for the process.
- *
- * Exceptions:
- * o When a stop signal is sent to a sleeping process that takes the
- * default action, the process is stopped without awakening it.
- * o SIGCONT restarts stopped processes (or puts them back to sleep)
- * regardless of the signal action (eg, blocked or ignored).
- *
- * Other ignored signals are discarded immediately.
- */
-void
-psignal_lock(p, signum, withlock)
- register struct proc *p;
- register int signum;
- register int withlock;
-{
- register int prop;
- register sig_t action;
- thread_t sig_thread_act;
- register task_t sig_task;
- int mask;
- struct uthread *uth;
- boolean_t funnel_state = FALSE;
- int sw_funnel = 0;
-
- if ((u_int)signum >= NSIG || signum == 0)
- panic("psignal signal number");
- mask = sigmask(signum);
- prop = sigprop[signum];
-
-#if SIGNAL_DEBUG
- if(rdebug_proc && (p == rdebug_proc)) {
- ram_printf(3);
- }
-#endif /* SIGNAL_DEBUG */
-
- if (thread_funnel_get() == (funnel_t *)0) {
- sw_funnel = 1;
- funnel_state = thread_funnel_set(kernel_flock, TRUE);
- }