signalvar.h revision 277697
116728Swpaul/*- 216728Swpaul * Copyright (c) 1991, 1993 316728Swpaul * The Regents of the University of California. All rights reserved. 416728Swpaul * 516728Swpaul * Redistribution and use in source and binary forms, with or without 616728Swpaul * modification, are permitted provided that the following conditions 716728Swpaul * are met: 816728Swpaul * 1. Redistributions of source code must retain the above copyright 916728Swpaul * notice, this list of conditions and the following disclaimer. 1016728Swpaul * 2. Redistributions in binary form must reproduce the above copyright 1116728Swpaul * notice, this list of conditions and the following disclaimer in the 1216728Swpaul * documentation and/or other materials provided with the distribution. 13262435Sbrueffer * 4. Neither the name of the University nor the names of its contributors 1416728Swpaul * may be used to endorse or promote products derived from this software 1516728Swpaul * without specific prior written permission. 1616728Swpaul * 1716728Swpaul * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 1816728Swpaul * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1916728Swpaul * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2016728Swpaul * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 2116728Swpaul * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2216728Swpaul * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2316728Swpaul * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2416728Swpaul * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2516728Swpaul * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2616728Swpaul * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2716728Swpaul * SUCH DAMAGE. 2816728Swpaul * 2916728Swpaul * @(#)signalvar.h 8.6 (Berkeley) 2/19/95 3031385Scharnier * $FreeBSD: stable/10/sys/sys/signalvar.h 277697 2015-01-25 13:09:53Z kib $ 3131385Scharnier */ 3216728Swpaul 3316728Swpaul#ifndef _SYS_SIGNALVAR_H_ 3431385Scharnier#define _SYS_SIGNALVAR_H_ 3550476Speter 3631385Scharnier#include <sys/queue.h> 3716728Swpaul#include <sys/_lock.h> 3816728Swpaul#include <sys/_mutex.h> 3916728Swpaul#include <sys/signal.h> 4016728Swpaul 4116728Swpaul/* 4216728Swpaul * Kernel signal definitions and data structures. 4316728Swpaul */ 4431385Scharnier 4516728Swpaul/* 4616728Swpaul * Logical process signal actions and state, needed only within the process 4716728Swpaul * The mapping between sigacts and proc structures is 1:1 except for rfork() 4816728Swpaul * processes masquerading as threads which use one structure for the whole 4916728Swpaul * group. All members are locked by the included mutex. The reference count 5016728Swpaul * and mutex must be last for the bcopy in sigacts_copy() to work. 5116728Swpaul */ 5290779Simpstruct sigacts { 5390779Simp sig_t ps_sigact[_SIG_MAXSIG]; /* Disposition of signals. */ 5416728Swpaul sigset_t ps_catchmask[_SIG_MAXSIG]; /* Signals to be blocked. */ 5516728Swpaul sigset_t ps_sigonstack; /* Signals to take on sigstack. */ 5616728Swpaul sigset_t ps_sigintr; /* Signals that interrupt syscalls. */ 5716728Swpaul sigset_t ps_sigreset; /* Signals that reset when caught. */ 5816728Swpaul sigset_t ps_signodefer; /* Signals not masked while handled. */ 5916728Swpaul sigset_t ps_siginfo; /* Signals that want SA_SIGINFO args. */ 6016728Swpaul sigset_t ps_sigignore; /* Signals being ignored. */ 6190779Simp sigset_t ps_sigcatch; /* Signals being caught by user. */ 6216728Swpaul sigset_t ps_freebsd4; /* Signals using freebsd4 ucontext. */ 6316728Swpaul sigset_t ps_osigset; /* Signals using <= 3.x osigset_t. */ 6416728Swpaul sigset_t ps_usertramp; /* SunOS compat; libc sigtramp. XXX */ 6516728Swpaul int ps_flag; 6616728Swpaul u_int ps_refcnt; 6716728Swpaul struct mtx ps_mtx; 6890779Simp}; 6916728Swpaul 7016728Swpaul#define PS_NOCLDWAIT 0x0001 /* No zombies if child dies */ 7116728Swpaul#define PS_NOCLDSTOP 0x0002 /* No SIGCHLD when children stop. */ 7216728Swpaul#define PS_CLDSIGIGN 0x0004 /* The SIGCHLD handler is SIG_IGN. */ 7316728Swpaul 7490779Simp#ifdef _KERNEL 7516728Swpaul 7616728Swpaul#ifdef COMPAT_43 7716728Swpaultypedef struct { 7816728Swpaul struct osigcontext si_sc; 7916728Swpaul int si_signo; 8090779Simp int si_code; 8116728Swpaul union sigval si_value; 8216728Swpaul} osiginfo_t; 8316728Swpaul 8416728Swpaulstruct osigaction { 8516728Swpaul union { 8616728Swpaul void (*__sa_handler)(int); 8716728Swpaul void (*__sa_sigaction)(int, osiginfo_t *, void *); 8816728Swpaul } __sigaction_u; /* signal handler */ 8990779Simp osigset_t sa_mask; /* signal mask to apply */ 9016728Swpaul int sa_flags; /* see signal options below */ 9116728Swpaul}; 9216728Swpaul 9316728Swpaultypedef void __osiginfohandler_t(int, osiginfo_t *, void *); 9416728Swpaul#endif /* COMPAT_43 */ 9590779Simp 9616728Swpaul/* additional signal action values, used only temporarily/internally */ 9716728Swpaul#define SIG_CATCH ((__sighandler_t *)2) 9816728Swpaul/* #define SIG_HOLD ((__sighandler_t *)3) See signal.h */ 9916728Swpaul 10016728Swpaul/* 10116728Swpaul * get signal action for process and signal; currently only for current process 10216728Swpaul */ 10316728Swpaul#define SIGACTION(p, sig) (p->p_sigacts->ps_sigact[_SIG_IDX(sig)]) 10490779Simp 10516728Swpaul#endif /* _KERNEL */ 10690779Simp 10716728Swpaul/* 10816728Swpaul * sigset_t manipulation macros. 10916728Swpaul */ 11016728Swpaul#define SIGADDSET(set, signo) \ 11116728Swpaul ((set).__bits[_SIG_WORD(signo)] |= _SIG_BIT(signo)) 11216728Swpaul 113229403Sed#define SIGDELSET(set, signo) \ 11416728Swpaul ((set).__bits[_SIG_WORD(signo)] &= ~_SIG_BIT(signo)) 11516728Swpaul 11616728Swpaul#define SIGEMPTYSET(set) \ 11716728Swpaul do { \ 11816728Swpaul int __i; \ 11916728Swpaul for (__i = 0; __i < _SIG_WORDS; __i++) \ 12016728Swpaul (set).__bits[__i] = 0; \ 12116728Swpaul } while (0) 12216728Swpaul 12316728Swpaul#define SIGFILLSET(set) \ 12416728Swpaul do { \ 125216227Skevlo int __i; \ 12616728Swpaul for (__i = 0; __i < _SIG_WORDS; __i++) \ 12716728Swpaul (set).__bits[__i] = ~0U; \ 12816728Swpaul } while (0) 12990779Simp 13016728Swpaul#define SIGISMEMBER(set, signo) \ 13116728Swpaul ((set).__bits[_SIG_WORD(signo)] & _SIG_BIT(signo)) 13225969Swpaul 13325969Swpaul#define SIGISEMPTY(set) (__sigisempty(&(set))) 13416728Swpaul#define SIGNOTEMPTY(set) (!__sigisempty(&(set))) 13516728Swpaul 13616728Swpaul#define SIGSETEQ(set1, set2) (__sigseteq(&(set1), &(set2))) 13716728Swpaul#define SIGSETNEQ(set1, set2) (!__sigseteq(&(set1), &(set2))) 13816728Swpaul 13916728Swpaul#define SIGSETOR(set1, set2) \ 14016728Swpaul do { \ 14116728Swpaul int __i; \ 14216728Swpaul for (__i = 0; __i < _SIG_WORDS; __i++) \ 14316728Swpaul (set1).__bits[__i] |= (set2).__bits[__i]; \ 14416728Swpaul } while (0) 14516728Swpaul 14616728Swpaul#define SIGSETAND(set1, set2) \ 14716728Swpaul do { \ 14816728Swpaul int __i; \ 14916728Swpaul for (__i = 0; __i < _SIG_WORDS; __i++) \ 15016728Swpaul (set1).__bits[__i] &= (set2).__bits[__i]; \ 15116728Swpaul } while (0) 15216728Swpaul 15316728Swpaul#define SIGSETNAND(set1, set2) \ 15416728Swpaul do { \ 15516728Swpaul int __i; \ 15616728Swpaul for (__i = 0; __i < _SIG_WORDS; __i++) \ 15716728Swpaul (set1).__bits[__i] &= ~(set2).__bits[__i]; \ 158 } while (0) 159 160#define SIGSETLO(set1, set2) ((set1).__bits[0] = (set2).__bits[0]) 161#define SIGSETOLD(set, oset) ((set).__bits[0] = (oset)) 162 163#define SIG_CANTMASK(set) \ 164 SIGDELSET(set, SIGKILL), SIGDELSET(set, SIGSTOP) 165 166#define SIG_STOPSIGMASK(set) \ 167 SIGDELSET(set, SIGSTOP), SIGDELSET(set, SIGTSTP), \ 168 SIGDELSET(set, SIGTTIN), SIGDELSET(set, SIGTTOU) 169 170#define SIG_CONTSIGMASK(set) \ 171 SIGDELSET(set, SIGCONT) 172 173#define sigcantmask (sigmask(SIGKILL) | sigmask(SIGSTOP)) 174 175#define SIG2OSIG(sig, osig) (osig = (sig).__bits[0]) 176#define OSIG2SIG(osig, sig) SIGEMPTYSET(sig); (sig).__bits[0] = osig 177 178static __inline int 179__sigisempty(sigset_t *set) 180{ 181 int i; 182 183 for (i = 0; i < _SIG_WORDS; i++) { 184 if (set->__bits[i]) 185 return (0); 186 } 187 return (1); 188} 189 190static __inline int 191__sigseteq(sigset_t *set1, sigset_t *set2) 192{ 193 int i; 194 195 for (i = 0; i < _SIG_WORDS; i++) { 196 if (set1->__bits[i] != set2->__bits[i]) 197 return (0); 198 } 199 return (1); 200} 201 202struct osigevent { 203 int sigev_notify; /* Notification type */ 204 union { 205 int __sigev_signo; /* Signal number */ 206 int __sigev_notify_kqueue; 207 } __sigev_u; 208 union sigval sigev_value; /* Signal value */ 209}; 210 211typedef struct ksiginfo { 212 TAILQ_ENTRY(ksiginfo) ksi_link; 213 siginfo_t ksi_info; 214 int ksi_flags; 215 struct sigqueue *ksi_sigq; 216} ksiginfo_t; 217 218#define ksi_signo ksi_info.si_signo 219#define ksi_errno ksi_info.si_errno 220#define ksi_code ksi_info.si_code 221#define ksi_pid ksi_info.si_pid 222#define ksi_uid ksi_info.si_uid 223#define ksi_status ksi_info.si_status 224#define ksi_addr ksi_info.si_addr 225#define ksi_value ksi_info.si_value 226#define ksi_band ksi_info.si_band 227#define ksi_trapno ksi_info.si_trapno 228#define ksi_overrun ksi_info.si_overrun 229#define ksi_timerid ksi_info.si_timerid 230#define ksi_mqd ksi_info.si_mqd 231 232/* bits for ksi_flags */ 233#define KSI_TRAP 0x01 /* Generated by trap. */ 234#define KSI_EXT 0x02 /* Externally managed ksi. */ 235#define KSI_INS 0x04 /* Directly insert ksi, not the copy */ 236#define KSI_SIGQ 0x08 /* Generated by sigqueue, might ret EGAIN. */ 237#define KSI_HEAD 0x10 /* Insert into head, not tail. */ 238#define KSI_COPYMASK (KSI_TRAP|KSI_SIGQ) 239 240#define KSI_ONQ(ksi) ((ksi)->ksi_sigq != NULL) 241 242typedef struct sigqueue { 243 sigset_t sq_signals; /* All pending signals. */ 244 sigset_t sq_kill; /* Legacy depth 1 queue. */ 245 TAILQ_HEAD(, ksiginfo) sq_list;/* Queued signal info. */ 246 struct proc *sq_proc; 247 int sq_flags; 248} sigqueue_t; 249 250/* Flags for ksi_flags */ 251#define SQ_INIT 0x01 252 253#ifdef _KERNEL 254 255/* Return nonzero if process p has an unmasked pending signal. */ 256#define SIGPENDING(td) \ 257 ((!SIGISEMPTY((td)->td_siglist) && \ 258 !sigsetmasked(&(td)->td_siglist, &(td)->td_sigmask)) || \ 259 (!SIGISEMPTY((td)->td_proc->p_siglist) && \ 260 !sigsetmasked(&(td)->td_proc->p_siglist, &(td)->td_sigmask))) 261/* 262 * Return the value of the pseudo-expression ((*set & ~*mask) != 0). This 263 * is an optimized version of SIGISEMPTY() on a temporary variable 264 * containing SIGSETNAND(*set, *mask). 265 */ 266static __inline int 267sigsetmasked(sigset_t *set, sigset_t *mask) 268{ 269 int i; 270 271 for (i = 0; i < _SIG_WORDS; i++) { 272 if (set->__bits[i] & ~mask->__bits[i]) 273 return (0); 274 } 275 return (1); 276} 277 278#define ksiginfo_init(ksi) \ 279do { \ 280 bzero(ksi, sizeof(ksiginfo_t)); \ 281} while(0) 282 283#define ksiginfo_init_trap(ksi) \ 284do { \ 285 ksiginfo_t *kp = ksi; \ 286 bzero(kp, sizeof(ksiginfo_t)); \ 287 kp->ksi_flags |= KSI_TRAP; \ 288} while(0) 289 290static __inline void 291ksiginfo_copy(ksiginfo_t *src, ksiginfo_t *dst) 292{ 293 (dst)->ksi_info = src->ksi_info; 294 (dst)->ksi_flags = (src->ksi_flags & KSI_COPYMASK); 295} 296 297static __inline void 298ksiginfo_set_sigev(ksiginfo_t *dst, struct sigevent *sigev) 299{ 300 dst->ksi_signo = sigev->sigev_signo; 301 dst->ksi_value = sigev->sigev_value; 302} 303 304struct pgrp; 305struct proc; 306struct sigio; 307struct thread; 308 309/* 310 * Lock the pointers for a sigio object in the underlying objects of 311 * a file descriptor. 312 */ 313#define SIGIO_LOCK() mtx_lock(&sigio_lock) 314#define SIGIO_TRYLOCK() mtx_trylock(&sigio_lock) 315#define SIGIO_UNLOCK() mtx_unlock(&sigio_lock) 316#define SIGIO_LOCKED() mtx_owned(&sigio_lock) 317#define SIGIO_ASSERT(type) mtx_assert(&sigio_lock, type) 318 319extern struct mtx sigio_lock; 320 321/* Flags for kern_sigprocmask(). */ 322#define SIGPROCMASK_OLD 0x0001 323#define SIGPROCMASK_PROC_LOCKED 0x0002 324#define SIGPROCMASK_PS_LOCKED 0x0004 325 326int cursig(struct thread *td); 327int sigdeferstop(void); 328int sigallowstop(void); 329void execsigs(struct proc *p); 330void gsignal(int pgid, int sig, ksiginfo_t *ksi); 331void killproc(struct proc *p, char *why); 332ksiginfo_t * ksiginfo_alloc(int wait); 333void ksiginfo_free(ksiginfo_t *ksi); 334int pksignal(struct proc *p, int sig, ksiginfo_t *ksi); 335void pgsigio(struct sigio **sigiop, int sig, int checkctty); 336void pgsignal(struct pgrp *pgrp, int sig, int checkctty, ksiginfo_t *ksi); 337int postsig(int sig); 338void kern_psignal(struct proc *p, int sig); 339int ptracestop(struct thread *td, int sig); 340void sendsig(sig_t catcher, ksiginfo_t *ksi, sigset_t *retmask); 341struct sigacts *sigacts_alloc(void); 342void sigacts_copy(struct sigacts *dest, struct sigacts *src); 343void sigacts_free(struct sigacts *ps); 344struct sigacts *sigacts_hold(struct sigacts *ps); 345int sigacts_shared(struct sigacts *ps); 346void sigexit(struct thread *td, int sig) __dead2; 347int sigev_findtd(struct proc *p, struct sigevent *sigev, struct thread **); 348int sig_ffs(sigset_t *set); 349void siginit(struct proc *p); 350void signotify(struct thread *td); 351void sigqueue_delete(struct sigqueue *queue, int sig); 352void sigqueue_delete_proc(struct proc *p, int sig); 353void sigqueue_flush(struct sigqueue *queue); 354void sigqueue_init(struct sigqueue *queue, struct proc *p); 355void sigqueue_take(ksiginfo_t *ksi); 356void tdksignal(struct thread *td, int sig, ksiginfo_t *ksi); 357int tdsendsignal(struct proc *p, struct thread *td, int sig, 358 ksiginfo_t *ksi); 359void tdsigcleanup(struct thread *td); 360void tdsignal(struct thread *td, int sig); 361void trapsignal(struct thread *td, ksiginfo_t *ksi); 362 363#endif /* _KERNEL */ 364 365#endif /* !_SYS_SIGNALVAR_H_ */ 366