blob: 2ffe6101908e52f937889340bd38ff3d96805cf2 [file] [log] [blame]
alaffincc2e5552000-07-27 17:13:18 +00001/*
2 * Copyright (c) 2000 Silicon Graphics, Inc. All Rights Reserved.
vapier45a8ba02009-07-20 10:59:32 +00003 *
alaffincc2e5552000-07-27 17:13:18 +00004 * This program is free software; you can redistribute it and/or modify it
5 * under the terms of version 2 of the GNU General Public License as
6 * published by the Free Software Foundation.
vapier45a8ba02009-07-20 10:59:32 +00007 *
alaffincc2e5552000-07-27 17:13:18 +00008 * This program is distributed in the hope that it would be useful, but
9 * WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
vapier45a8ba02009-07-20 10:59:32 +000011 *
alaffincc2e5552000-07-27 17:13:18 +000012 * Further, this software is distributed without any warranty that it is
13 * free of the rightful claim of any third person regarding infringement
14 * or the like. Any license provided herein, whether implied or
15 * otherwise, applies only to this software file. Patent licenses, if
16 * any, provided herein do not apply to combinations of this program with
17 * other software, or any other product whatsoever.
vapier45a8ba02009-07-20 10:59:32 +000018 *
alaffincc2e5552000-07-27 17:13:18 +000019 * You should have received a copy of the GNU General Public License along
Wanlong Gaofed96412012-10-24 10:10:29 +080020 * with this program; if not, write the Free Software Foundation, Inc.,
21 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
vapier45a8ba02009-07-20 10:59:32 +000022 *
alaffincc2e5552000-07-27 17:13:18 +000023 * Contact information: Silicon Graphics, Inc., 1600 Amphitheatre Pkwy,
24 * Mountain View, CA 94043, or:
vapier45a8ba02009-07-20 10:59:32 +000025 *
26 * http://www.sgi.com
27 *
28 * For further information regarding this notice, see:
29 *
alaffincc2e5552000-07-27 17:13:18 +000030 * http://oss.sgi.com/projects/GenInfo/NoticeExplan/
31 */
32
vapier6daba922009-08-28 09:29:01 +000033/* $Id: tst_sig.c,v 1.13 2009/08/28 09:29:01 vapier Exp $ */
alaffincc2e5552000-07-27 17:13:18 +000034
35/*****************************************************************************
36 OS Testing - Silicon Graphics, Inc.
37
38 FUNCTION IDENTIFIER : tst_sig Set up for unexpected signals.
39
40 AUTHOR : David D. Fenner
41
42 CO-PILOT : Bill Roske
43
44 DATE STARTED : 06/06/90
45
46 This module may be linked with c-modules requiring unexpected
47 signal handling. The parameters to tst_sig are as follows:
48
49 fork_flag - set to FORK or NOFORK depending upon whether the
50 calling program executes a fork() system call. It
51 is normally the case that the calling program treats
52 SIGCLD as an expected signal if fork() is being used.
53
54 handler - a pointer to the unexpected signal handler to
55 be executed after an unexpected signal has been
vapier45a8ba02009-07-20 10:59:32 +000056 detected. If handler is set to DEF_HANDLER, a
alaffincc2e5552000-07-27 17:13:18 +000057 default handler is used. This routine should be
58 declared as function returning an int.
59
60 cleanup - a pointer to a cleanup routine to be executed
61 by the unexpected signal handler before tst_exit is
62 called. This parameter is set to NULL if no cleanup
63 routine is required. An external variable, T_cleanup
vapier45a8ba02009-07-20 10:59:32 +000064 is set so that other user-defined handlers have
alaffincc2e5552000-07-27 17:13:18 +000065 access to the cleanup routine. This routine should be
66 declared as returning type void.
67
68***************************************************************************/
69
alaffincc2e5552000-07-27 17:13:18 +000070#include <errno.h>
71#include <string.h>
72#include <signal.h>
mridgee6508f82005-01-04 21:00:17 +000073#include <unistd.h>
alaffincc2e5552000-07-27 17:13:18 +000074#include "test.h"
75
76#define MAXMESG 150 /* size of mesg string sent to tst_res */
77
vapier6daba922009-08-28 09:29:01 +000078void (*T_cleanup) (); /* pointer to cleanup function */
alaffincc2e5552000-07-27 17:13:18 +000079
nstrazd8522012001-06-01 19:46:13 +000080/****************************************************************************
81 * STD_COPIES is defined in parse_opts.c but is externed here in order to
82 * test whether SIGCHILD should be ignored or not.
83 ***************************************************************************/
84extern int STD_COPIES;
85
vapier6daba922009-08-28 09:29:01 +000086static void def_handler(); /* default signal handler */
87static void (*tst_setup_signal(int, void (*)(int))) (int);
alaffincc2e5552000-07-27 17:13:18 +000088
89/****************************************************************************
90 * tst_sig() : set-up to catch unexpected signals. fork_flag is set to NOFORK
91 * if SIGCLD is to be an "unexpected signal", otherwise it is set to
92 * FORK. cleanup points to a cleanup routine to be executed before
93 * tst_exit is called (cleanup is set to NULL if no cleanup is desired).
94 * handler is a pointer to the signal handling routine (if handler is
95 * set to NULL, a default handler is used).
96 ***************************************************************************/
97
vapier6daba922009-08-28 09:29:01 +000098void tst_sig(int fork_flag, void (*handler) (), void (*cleanup) ())
alaffincc2e5552000-07-27 17:13:18 +000099{
alaffincc2e5552000-07-27 17:13:18 +0000100 int sig;
mridgee6508f82005-01-04 21:00:17 +0000101#ifdef _SC_SIGRT_MIN
vapier6daba922009-08-28 09:29:01 +0000102 long sigrtmin, sigrtmax;
mridgee6508f82005-01-04 21:00:17 +0000103#endif
alaffincc2e5552000-07-27 17:13:18 +0000104
105 /*
106 * save T_cleanup and handler function pointers
107 */
vapier6daba922009-08-28 09:29:01 +0000108 T_cleanup = cleanup; /* used by default handler */
alaffincc2e5552000-07-27 17:13:18 +0000109
110 if (handler == DEF_HANDLER) {
111 /* use default handler */
112 handler = def_handler;
113 }
mridgee6508f82005-01-04 21:00:17 +0000114#ifdef _SC_SIGRT_MIN
vapier6daba922009-08-28 09:29:01 +0000115 sigrtmin = sysconf(_SC_SIGRT_MIN);
116 sigrtmax = sysconf(_SC_SIGRT_MAX);
mridgee6508f82005-01-04 21:00:17 +0000117#endif
118
alaffincc2e5552000-07-27 17:13:18 +0000119 /*
120 * now loop through all signals and set the handlers
121 */
122
123 for (sig = 1; sig < NSIG; sig++) {
vapier6daba922009-08-28 09:29:01 +0000124 /*
125 * SIGKILL is never unexpected.
126 * SIGCLD is only unexpected when
127 * no forking is being done.
128 * SIGINFO is used for file quotas and should be expected
129 */
alaffincc2e5552000-07-27 17:13:18 +0000130
mridgee6508f82005-01-04 21:00:17 +0000131#ifdef _SC_SIGRT_MIN
vapier6daba922009-08-28 09:29:01 +0000132 if (sig >= sigrtmin && sig <= sigrtmax)
133 continue;
mridgee6508f82005-01-04 21:00:17 +0000134#endif
135
vapier6daba922009-08-28 09:29:01 +0000136 switch (sig) {
137 case SIGKILL:
138 case SIGSTOP:
139 case SIGCONT:
mridgee6508f82005-01-04 21:00:17 +0000140#if !defined(_SC_SIGRT_MIN) && defined(__SIGRTMIN) && defined(__SIGRTMAX)
vapier6daba922009-08-28 09:29:01 +0000141 /* Ignore all real-time signals */
robbiew3e36a842003-11-25 16:04:28 +0000142 case __SIGRTMIN:
vapier6daba922009-08-28 09:29:01 +0000143 case __SIGRTMIN + 1:
144 case __SIGRTMIN + 2:
145 case __SIGRTMIN + 3:
146 case __SIGRTMIN + 4:
147 case __SIGRTMIN + 5:
148 case __SIGRTMIN + 6:
149 case __SIGRTMIN + 7:
150 case __SIGRTMIN + 8:
151 case __SIGRTMIN + 9:
152 case __SIGRTMIN + 10:
153 case __SIGRTMIN + 11:
154 case __SIGRTMIN + 12:
155 case __SIGRTMIN + 13:
156 case __SIGRTMIN + 14:
157 case __SIGRTMIN + 15:
robbiew79c135c2004-05-19 20:44:50 +0000158/* __SIGRTMIN is 37 on HPPA rather than 32 *
159 * as on i386, etc. */
160#if !defined(__hppa__)
vapier6daba922009-08-28 09:29:01 +0000161 case __SIGRTMAX - 15:
162 case __SIGRTMAX - 14:
163 case __SIGRTMAX - 13:
164 case __SIGRTMAX - 12:
165 case __SIGRTMAX - 11:
robbiew79c135c2004-05-19 20:44:50 +0000166#endif
vapier6daba922009-08-28 09:29:01 +0000167 case __SIGRTMAX - 10:
168 case __SIGRTMAX - 9:
169 case __SIGRTMAX - 8:
170 case __SIGRTMAX - 7:
171 case __SIGRTMAX - 6:
172 case __SIGRTMAX - 5:
173 case __SIGRTMAX - 4:
174 case __SIGRTMAX - 3:
175 case __SIGRTMAX - 2:
176 case __SIGRTMAX - 1:
robbiew3e36a842003-11-25 16:04:28 +0000177 case __SIGRTMAX:
mridgee6508f82005-01-04 21:00:17 +0000178#endif
alaffincc2e5552000-07-27 17:13:18 +0000179#ifdef CRAY
vapier6daba922009-08-28 09:29:01 +0000180 case SIGINFO:
181 case SIGRECOVERY: /* allow chkpnt/restart */
Wanlong Gao354ebb42012-12-07 10:10:04 +0800182#endif /* CRAY */
alaffincc2e5552000-07-27 17:13:18 +0000183
184#ifdef SIGSWAP
robbiew3e36a842003-11-25 16:04:28 +0000185 case SIGSWAP:
Wanlong Gao354ebb42012-12-07 10:10:04 +0800186#endif /* SIGSWAP */
alaffincc2e5552000-07-27 17:13:18 +0000187
188#ifdef SIGCKPT
vapier6daba922009-08-28 09:29:01 +0000189 case SIGCKPT:
alaffincc2e5552000-07-27 17:13:18 +0000190#endif
191#ifdef SIGRESTART
vapier6daba922009-08-28 09:29:01 +0000192 case SIGRESTART:
alaffincc2e5552000-07-27 17:13:18 +0000193#endif
vapier6daba922009-08-28 09:29:01 +0000194 /*
195 * pthread-private signals SIGPTINTR and SIGPTRESCHED.
196 * Setting a handler for these signals is disallowed when
197 * the binary is linked against libpthread.
198 */
alaffincc2e5552000-07-27 17:13:18 +0000199#ifdef SIGPTINTR
vapier6daba922009-08-28 09:29:01 +0000200 case SIGPTINTR:
Wanlong Gao354ebb42012-12-07 10:10:04 +0800201#endif /* SIGPTINTR */
alaffincc2e5552000-07-27 17:13:18 +0000202#ifdef SIGPTRESCHED
vapier6daba922009-08-28 09:29:01 +0000203 case SIGPTRESCHED:
Wanlong Gao354ebb42012-12-07 10:10:04 +0800204#endif /* SIGPTRESCHED */
mridgee6508f82005-01-04 21:00:17 +0000205#ifdef _SIGRESERVE
vapier6daba922009-08-28 09:29:01 +0000206 case _SIGRESERVE:
mridgee6508f82005-01-04 21:00:17 +0000207#endif
208#ifdef _SIGDIL
vapier6daba922009-08-28 09:29:01 +0000209 case _SIGDIL:
mridgee6508f82005-01-04 21:00:17 +0000210#endif
211#ifdef _SIGCANCEL
vapier6daba922009-08-28 09:29:01 +0000212 case _SIGCANCEL:
mridgee6508f82005-01-04 21:00:17 +0000213#endif
214#ifdef _SIGGFAULT
vapier6daba922009-08-28 09:29:01 +0000215 case _SIGGFAULT:
mridgee6508f82005-01-04 21:00:17 +0000216#endif
vapier6daba922009-08-28 09:29:01 +0000217 break;
alaffincc2e5552000-07-27 17:13:18 +0000218
vapier6daba922009-08-28 09:29:01 +0000219 case SIGCLD:
220 if (fork_flag == FORK || STD_COPIES > 1)
221 continue;
alaffincc2e5552000-07-27 17:13:18 +0000222
vapier6daba922009-08-28 09:29:01 +0000223 default:
224 if (tst_setup_signal(sig, handler) == SIG_ERR)
Wanlong Gao354ebb42012-12-07 10:10:04 +0800225 tst_resm(TWARN | TERRNO,
226 "signal failed for signal %d", sig);
vapier6daba922009-08-28 09:29:01 +0000227 break;
228 }
alaffincc2e5552000-07-27 17:13:18 +0000229#ifdef __sgi
vapier6daba922009-08-28 09:29:01 +0000230 /* On irix (07/96), signal() fails when signo is 33 or higher */
231 if (sig + 1 >= 33)
232 break;
Wanlong Gao354ebb42012-12-07 10:10:04 +0800233#endif /* __sgi */
alaffincc2e5552000-07-27 17:13:18 +0000234
vapier6daba922009-08-28 09:29:01 +0000235 } /* endfor */
alaffincc2e5552000-07-27 17:13:18 +0000236}
237
alaffincc2e5552000-07-27 17:13:18 +0000238/****************************************************************************
239 * def_handler() : default signal handler that is invoked when
240 * an unexpected signal is caught.
241 ***************************************************************************/
242
vapier6daba922009-08-28 09:29:01 +0000243static void def_handler(int sig)
alaffincc2e5552000-07-27 17:13:18 +0000244{
alaffincc2e5552000-07-27 17:13:18 +0000245 /*
vapier6daba922009-08-28 09:29:01 +0000246 * Break remaining test cases, do any cleanup, then exit
alaffincc2e5552000-07-27 17:13:18 +0000247 */
Garrett Cooper6a464fe2010-12-18 06:32:42 -0800248 tst_brkm(TBROK, T_cleanup,
Wanlong Gao354ebb42012-12-07 10:10:04 +0800249 "unexpected signal %d received (pid = %d).", sig, getpid());
alaffincc2e5552000-07-27 17:13:18 +0000250}
alaffin3c8699d2000-09-07 14:34:44 +0000251
252/*
253 * tst_setup_signal - A function like signal(), but we have
254 * control over its personality.
255 */
Wanlong Gao354ebb42012-12-07 10:10:04 +0800256static void (*tst_setup_signal(int sig, void (*handler) (int))) (int) {
vapier6daba922009-08-28 09:29:01 +0000257 struct sigaction my_act, old_act;
258 int ret;
alaffin3c8699d2000-09-07 14:34:44 +0000259
vapier6daba922009-08-28 09:29:01 +0000260 my_act.sa_handler = handler;
261 my_act.sa_flags = SA_RESTART;
262 sigemptyset(&my_act.sa_mask);
alaffin3c8699d2000-09-07 14:34:44 +0000263
vapier6daba922009-08-28 09:29:01 +0000264 ret = sigaction(sig, &my_act, &old_act);
alaffin3c8699d2000-09-07 14:34:44 +0000265
vapier6daba922009-08-28 09:29:01 +0000266 if (ret == 0)
267 return old_act.sa_handler;
268 else
269 return SIG_ERR;
Chris Dearmanec6edca2012-10-17 19:54:01 -0700270}