Imported from ../bash-3.1.tar.gz.
[platform/upstream/bash.git] / support / mksignames.c
1 /* signames.c -- Create and write `signames.h', which contains an array of
2    signal names. */
3
4 /* Copyright (C) 1992-2003 Free Software Foundation, Inc.
5
6    This file is part of GNU Bash, the Bourne Again SHell.
7
8    Bash is free software; you can redistribute it and/or modify it under
9    the terms of the GNU General Public License as published by the Free
10    Software Foundation; either version 2, or (at your option) any later
11    version.
12
13    Bash is distributed in the hope that it will be useful, but WITHOUT ANY
14    WARRANTY; without even the implied warranty of MERCHANTABILITY or
15    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
16    for more details.
17
18    You should have received a copy of the GNU General Public License along
19    with Bash; see the file COPYING.  If not, write to the Free Software
20    Foundation, 59 Temple Place, Suite 330, Boston, MA 02111 USA. */
21
22 #include <config.h>
23
24 #include <stdio.h>
25 #include <sys/types.h>
26 #include <signal.h>
27 #if defined (HAVE_STDLIB_H)
28 #  include <stdlib.h>
29 #else
30 #  include "ansi_stdlib.h"
31 #endif /* HAVE_STDLIB_H */
32
33 #if !defined (NSIG)
34 #  define NSIG 64
35 #endif
36
37 /*
38  * Special traps:
39  *      EXIT == 0
40  *      DEBUG == NSIG
41  *      ERR == NSIG+1
42  *      RETURN == NSIG+2
43  */
44 #define LASTSIG NSIG+2
45
46 char *signal_names[2 * (LASTSIG)];
47
48 #define signal_names_size (sizeof(signal_names)/sizeof(signal_names[0]))
49
50 char *progname;
51
52 /* AIX 4.3 defines SIGRTMIN and SIGRTMAX as 888 and 999 respectively.
53    I don't want to allocate so much unused space for the intervening signal
54    numbers, so we just punt if SIGRTMAX is past the bounds of the
55    signal_names array (handled in configure). */
56 #if defined (SIGRTMAX) && defined (UNUSABLE_RT_SIGNALS)
57 #  undef SIGRTMAX
58 #  undef SIGRTMIN
59 #endif
60
61 #if defined (SIGRTMAX) || defined (SIGRTMIN)
62 #  define RTLEN 14
63 #  define RTLIM 256
64 #endif
65
66 void
67 initialize_signames ()
68 {
69   register int i;
70 #if defined (SIGRTMAX) || defined (SIGRTMIN)
71   int rtmin, rtmax, rtcnt;
72 #endif
73
74   for (i = 1; i < signal_names_size; i++)
75     signal_names[i] = (char *)NULL;
76
77   /* `signal' 0 is what we do on exit. */
78   signal_names[0] = "EXIT";
79
80   /* Place signal names which can be aliases for more common signal
81      names first.  This allows (for example) SIGABRT to overwrite SIGLOST. */
82
83   /* POSIX 1003.1b-1993 real time signals, but take care of incomplete
84      implementations. Acoording to the standard, both, SIGRTMIN and
85      SIGRTMAX must be defined, SIGRTMIN must be stricly less than
86      SIGRTMAX, and the difference must be at least 7, that is, there
87      must be at least eight distinct real time signals. */
88
89   /* The generated signal names are SIGRTMIN, SIGRTMIN+1, ...,
90      SIGRTMIN+x, SIGRTMAX-x, ..., SIGRTMAX-1, SIGRTMAX. If the number
91      of RT signals is odd, there is an extra SIGRTMIN+(x+1).
92      These names are the ones used by ksh and /usr/xpg4/bin/sh on SunOS5. */
93
94 #if defined (SIGRTMIN)
95   rtmin = SIGRTMIN;
96   signal_names[rtmin] = "SIGRTMIN";
97 #endif
98
99 #if defined (SIGRTMAX)
100   rtmax = SIGRTMAX;
101   signal_names[rtmax] = "SIGRTMAX";
102 #endif
103
104 #if defined (SIGRTMAX) && defined (SIGRTMIN)
105   if (rtmax > rtmin)
106     {
107       rtcnt = (rtmax - rtmin - 1) / 2;
108       /* croak if there are too many RT signals */
109       if (rtcnt >= RTLIM/2)
110         {
111           rtcnt = RTLIM/2-1;
112           fprintf(stderr, "%s: error: more than %i real time signals, fix `%s'\n",
113                   progname, RTLIM, progname);
114         }
115
116       for (i = 1; i <= rtcnt; i++)
117         {
118           signal_names[rtmin+i] = (char *)malloc(RTLEN);
119           if (signal_names[rtmin+i])
120             sprintf (signal_names[rtmin+i], "SIGRTMIN+%d", i);
121           signal_names[rtmax-i] = (char *)malloc(RTLEN);
122           if (signal_names[rtmax-i])
123             sprintf (signal_names[rtmax-i], "SIGRTMAX-%d", i);
124         }
125
126       if (rtcnt < RTLIM/2-1 && rtcnt != (rtmax-rtmin)/2)
127         {
128           /* Need an extra RTMIN signal */
129           signal_names[rtmin+rtcnt+1] = (char *)malloc(RTLEN);
130           if (signal_names[rtmin+rtcnt+1])
131             sprintf (signal_names[rtmin+rtcnt+1], "SIGRTMIN+%d", rtcnt+1);
132         }
133     }
134 #endif /* SIGRTMIN && SIGRTMAX */
135
136 #if defined (SIGLOST)   /* resource lost (eg, record-lock lost) */
137   signal_names[SIGLOST] = "SIGLOST";
138 #endif
139
140 /* AIX */
141 #if defined (SIGMSG)    /* HFT input data pending */
142   signal_names[SIGMSG] = "SIGMSG";
143 #endif
144
145 #if defined (SIGDANGER) /* system crash imminent */
146   signal_names[SIGDANGER] = "SIGDANGER";
147 #endif
148
149 #if defined (SIGMIGRATE) /* migrate process to another CPU */
150   signal_names[SIGMIGRATE] = "SIGMIGRATE";
151 #endif
152
153 #if defined (SIGPRE)    /* programming error */
154   signal_names[SIGPRE] = "SIGPRE";
155 #endif
156
157 #if defined (SIGVIRT)   /* AIX virtual time alarm */
158   signal_names[SIGVIRT] = "SIGVIRT";
159 #endif
160
161 #if defined (SIGALRM1)  /* m:n condition variables */
162   signal_names[SIGALRM1] = "SIGALRM1";
163 #endif
164
165 #if defined (SIGWAITING)        /* m:n scheduling */
166   signal_names[SIGWAITING] = "SIGWAITING";
167 #endif
168
169 #if defined (SIGGRANT)  /* HFT monitor mode granted */
170   signal_names[SIGGRANT] = "SIGGRANT";
171 #endif
172
173 #if defined (SIGKAP)    /* keep alive poll from native keyboard */
174   signal_names[SIGKAP] = "SIGKAP";
175 #endif
176
177 #if defined (SIGRETRACT) /* HFT monitor mode retracted */
178   signal_names[SIGRETRACT] = "SIGRETRACT";
179 #endif
180
181 #if defined (SIGSOUND)  /* HFT sound sequence has completed */
182   signal_names[SIGSOUND] = "SIGSOUND";
183 #endif
184
185 #if defined (SIGSAK)    /* Secure Attention Key */
186   signal_names[SIGSAK] = "SIGSAK";
187 #endif
188
189 /* SunOS5 */
190 #if defined (SIGLWP)    /* special signal used by thread library */
191   signal_names[SIGLWP] = "SIGLWP";
192 #endif
193
194 #if defined (SIGFREEZE) /* special signal used by CPR */
195   signal_names[SIGFREEZE] = "SIGFREEZE";
196 #endif
197
198 #if defined (SIGTHAW)   /* special signal used by CPR */
199   signal_names[SIGTHAW] = "SIGTHAW";
200 #endif
201
202 #if defined (SIGCANCEL) /* thread cancellation signal used by libthread */
203   signal_names[SIGCANCEL] = "SIGCANCEL";
204 #endif
205
206 #if defined (SIGXRES)   /* resource control exceeded */
207   signal_names[SIGXRES] = "SIGXRES";
208 #endif
209
210 /* HP-UX */
211 #if defined (SIGDIL)    /* DIL signal (?) */
212   signal_names[SIGDIL] = "SIGDIL";
213 #endif
214
215 /* System V */
216 #if defined (SIGCLD)    /* Like SIGCHLD.  */
217   signal_names[SIGCLD] = "SIGCLD";
218 #endif
219
220 #if defined (SIGPWR)    /* power state indication */
221   signal_names[SIGPWR] = "SIGPWR";
222 #endif
223
224 #if defined (SIGPOLL)   /* Pollable event (for streams)  */
225   signal_names[SIGPOLL] = "SIGPOLL";
226 #endif
227
228 /* Unknown */
229 #if defined (SIGWINDOW)
230   signal_names[SIGWINDOW] = "SIGWINDOW";
231 #endif
232
233 /* Linux */
234 #if defined (SIGSTKFLT)
235   signal_names[SIGSTKFLT] = "SIGSTKFLT";
236 #endif
237
238 /* FreeBSD */
239 #if defined (SIGTHR)    /* thread interrupt */
240   signal_names[SIGTHR] = "SIGTHR";
241 #endif
242
243 /* Common */
244 #if defined (SIGHUP)    /* hangup */
245   signal_names[SIGHUP] = "SIGHUP";
246 #endif
247
248 #if defined (SIGINT)    /* interrupt */
249   signal_names[SIGINT] = "SIGINT";
250 #endif
251
252 #if defined (SIGQUIT)   /* quit */
253   signal_names[SIGQUIT] = "SIGQUIT";
254 #endif
255
256 #if defined (SIGILL)    /* illegal instruction (not reset when caught) */
257   signal_names[SIGILL] = "SIGILL";
258 #endif
259
260 #if defined (SIGTRAP)   /* trace trap (not reset when caught) */
261   signal_names[SIGTRAP] = "SIGTRAP";
262 #endif
263
264 #if defined (SIGIOT)    /* IOT instruction */
265   signal_names[SIGIOT] = "SIGIOT";
266 #endif
267
268 #if defined (SIGABRT)   /* Cause current process to dump core. */
269   signal_names[SIGABRT] = "SIGABRT";
270 #endif
271
272 #if defined (SIGEMT)    /* EMT instruction */
273   signal_names[SIGEMT] = "SIGEMT";
274 #endif
275
276 #if defined (SIGFPE)    /* floating point exception */
277   signal_names[SIGFPE] = "SIGFPE";
278 #endif
279
280 #if defined (SIGKILL)   /* kill (cannot be caught or ignored) */
281   signal_names[SIGKILL] = "SIGKILL";
282 #endif
283
284 #if defined (SIGBUS)    /* bus error */
285   signal_names[SIGBUS] = "SIGBUS";
286 #endif
287
288 #if defined (SIGSEGV)   /* segmentation violation */
289   signal_names[SIGSEGV] = "SIGSEGV";
290 #endif
291
292 #if defined (SIGSYS)    /* bad argument to system call */
293   signal_names[SIGSYS] = "SIGSYS";
294 #endif
295
296 #if defined (SIGPIPE)   /* write on a pipe with no one to read it */
297   signal_names[SIGPIPE] = "SIGPIPE";
298 #endif
299
300 #if defined (SIGALRM)   /* alarm clock */
301   signal_names[SIGALRM] = "SIGALRM";
302 #endif
303
304 #if defined (SIGTERM)   /* software termination signal from kill */
305   signal_names[SIGTERM] = "SIGTERM";
306 #endif
307
308 #if defined (SIGURG)    /* urgent condition on IO channel */
309   signal_names[SIGURG] = "SIGURG";
310 #endif
311
312 #if defined (SIGSTOP)   /* sendable stop signal not from tty */
313   signal_names[SIGSTOP] = "SIGSTOP";
314 #endif
315
316 #if defined (SIGTSTP)   /* stop signal from tty */
317   signal_names[SIGTSTP] = "SIGTSTP";
318 #endif
319
320 #if defined (SIGCONT)   /* continue a stopped process */
321   signal_names[SIGCONT] = "SIGCONT";
322 #endif
323
324 #if defined (SIGCHLD)   /* to parent on child stop or exit */
325   signal_names[SIGCHLD] = "SIGCHLD";
326 #endif
327
328 #if defined (SIGTTIN)   /* to readers pgrp upon background tty read */
329   signal_names[SIGTTIN] = "SIGTTIN";
330 #endif
331
332 #if defined (SIGTTOU)   /* like TTIN for output if (tp->t_local&LTOSTOP) */
333   signal_names[SIGTTOU] = "SIGTTOU";
334 #endif
335
336 #if defined (SIGIO)     /* input/output possible signal */
337   signal_names[SIGIO] = "SIGIO";
338 #endif
339
340 #if defined (SIGXCPU)   /* exceeded CPU time limit */
341   signal_names[SIGXCPU] = "SIGXCPU";
342 #endif
343
344 #if defined (SIGXFSZ)   /* exceeded file size limit */
345   signal_names[SIGXFSZ] = "SIGXFSZ";
346 #endif
347
348 #if defined (SIGVTALRM) /* virtual time alarm */
349   signal_names[SIGVTALRM] = "SIGVTALRM";
350 #endif
351
352 #if defined (SIGPROF)   /* profiling time alarm */
353   signal_names[SIGPROF] = "SIGPROF";
354 #endif
355
356 #if defined (SIGWINCH)  /* window changed */
357   signal_names[SIGWINCH] = "SIGWINCH";
358 #endif
359
360 /* 4.4 BSD */
361 #if defined (SIGINFO) && !defined (_SEQUENT_)   /* information request */
362   signal_names[SIGINFO] = "SIGINFO";
363 #endif
364
365 #if defined (SIGUSR1)   /* user defined signal 1 */
366   signal_names[SIGUSR1] = "SIGUSR1";
367 #endif
368
369 #if defined (SIGUSR2)   /* user defined signal 2 */
370   signal_names[SIGUSR2] = "SIGUSR2";
371 #endif
372
373 #if defined (SIGKILLTHR)        /* BeOS: Kill Thread */
374   signal_names[SIGKILLTHR] = "SIGKILLTHR";
375 #endif
376
377   for (i = 0; i < NSIG; i++)
378     if (signal_names[i] == (char *)NULL)
379       {
380         signal_names[i] = (char *)malloc (18);
381         if (signal_names[i])
382           sprintf (signal_names[i], "SIGJUNK(%d)", i);
383       }
384
385   signal_names[NSIG] = "DEBUG";
386   signal_names[NSIG+1] = "ERR";
387   signal_names[NSIG+2] = "RETURN";
388 }
389
390 void
391 write_signames (stream)
392      FILE *stream;
393 {
394   register int i;
395
396   fprintf (stream, "/* This file was automatically created by %s.\n",
397            progname);
398   fprintf (stream, "   Do not edit.  Edit support/mksignames.c instead. */\n\n");
399   fprintf (stream,
400            "/* A translation list so we can be polite to our users. */\n");
401   fprintf (stream, "char *signal_names[NSIG + 4] = {\n");
402
403   for (i = 0; i <= LASTSIG; i++)
404     fprintf (stream, "    \"%s\",\n", signal_names[i]);
405
406   fprintf (stream, "    (char *)0x0\n");
407   fprintf (stream, "};\n");
408 }
409
410 int
411 main (argc, argv)
412      int argc;
413      char **argv;
414 {
415   char *stream_name;
416   FILE *stream;
417
418   progname = argv[0];
419
420   if (argc == 1)
421     {
422       stream_name = "stdout";
423       stream = stdout;
424     }
425   else if (argc == 2)
426     {
427       stream_name = argv[1];
428       stream = fopen (stream_name, "w");
429     }
430   else
431     {
432       fprintf (stderr, "Usage: %s [output-file]\n", progname);
433       exit (1);
434     }
435
436   if (!stream)
437     {
438       fprintf (stderr, "%s: %s: cannot open for writing\n",
439                progname, stream_name);
440       exit (2);
441     }
442
443   initialize_signames ();
444   write_signames (stream);
445   exit (0);
446 }