|
|
1.1 root 1: /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
2:
3: /*
4: $Header: b3sig.c,v 1.4 85/08/27 10:56:21 timo Exp $
5: */
6:
7: /*Handle interrupts and signals*/
8:
9: #include "b.h"
10: #include "b0fea.h"
11: #include "b1obj.h"
12: #include "b0con.h"
13: #include "b3scr.h"
14: #include "b3err.h"
15: #include "b3env.h"
16: #ifdef SETJMP
17: #include <setjmp.h>
18: #endif
19:
20: #ifdef SIGNAL
21: #include <signal.h>
22: #endif
23:
24: /*The operating system provides a function signal(s,f)
25: that associates function f with the signal s, and returns
26: a pointer to the previous function associated with s.
27: Then, when signal s occurs, f is called and the function associated with s
28: may or may not be reset. Thus f may need to call signal(s,f) again to.
29: The code here doesn't depend on either interpretation, always being explicit
30: about which handler to use.
31:
32: There are two signals that can come from the user: quit and interrupt.
33: Interrupt should just stop the interpreter and return to B command level;
34: quit should stop the B system completely.
35: All other signals are caused by errors (eg memory exhausted)
36: or come from outside the program, and are therefore fatal.
37:
38: SIG_IGN is the system supplied routine to ignore a signal.
39: SIG_DFL is the system supplied default for a signal.
40: kill(getpid(), signal) kills the program according to 'signal'
41:
42: On BSD systems, SIGTSTP and other signals causing the process to be
43: suspended, and SIGCONT and others that are ignored by default,
44: must not be caught. It is assumed that all these are defined
45: when SIGTSTP is defined.
46: */
47:
48: #ifdef SIGTSTP
49: Hidden bool must_handle(sig) int sig; {
50: /* Shouldn't we enumerate the list of signals we *do* want to catch? */
51: /* It seems that new signals are all of the type that should be
52: ignored by most processes... */
53: switch (sig) {
54: case SIGURG:
55: case SIGSTOP:
56: case SIGTSTP:
57: case SIGCONT:
58: case SIGCHLD:
59: case SIGTTIN:
60: case SIGTTOU:
61: case SIGIO:
62: return No;
63: default:
64: return Yes;
65: }
66: }
67: #else
68: #ifdef SIGCLD /* System V */
69: #define must_handle(sig) ((sig) != SIGCLD)
70: #else
71: #define must_handle(sig) Yes
72: #endif
73: #endif
74:
75: #ifdef NOT_USED
76: Visible Procedure dump() {
77: if (cntxt != In_prmnv) putprmnv();
78: #ifdef KILL
79: signal(SIGQUIT, SIG_DFL);
80: kill(getpid(), SIGQUIT);
81: #else
82: exit(-1);
83: #endif
84: }
85: #endif NOT_USED
86:
87: #ifdef SIGNAL
88: Hidden Procedure oops(sig, m) int sig; string m; {
89: signal(sig, SIG_DFL); /* Don't call handler recursive -- just die... */
90: #ifdef sigmask /* 4.2 BSD */
91: sigsetmask(0); /* Don't block signals in handler -- just die... */
92: #endif
93: #ifdef EXT_COMMAND
94: e_done();
95: #endif
96: fflush(stdout);
97: fprintf(stdout, "*** Oops, %s\n", m);
98: fflush(stdout);
99: if (cntxt != In_prmnv) putprmnv();
100: #ifdef KILL
101: kill(getpid(), sig);
102: #else
103: exit(-1);
104: #endif
105: }
106:
107: Hidden Procedure burp(sig) int sig; {
108: oops(sig,
109: "I feel suddenly (BURP!) indisposed. I'll call it a day. Sorry.");
110: }
111:
112: Hidden Procedure aog(sig) int sig; {
113: oops(sig,
114: "an act of God has occurred compelling me to discontinue service.");
115: }
116:
117: Hidden Procedure fpe_signal(sig) int sig; {
118: signal(sig /* == SIGFPE*/, fpe_signal);
119: syserr(MESS(3900, "unexpected arithmetic overflow"));
120: }
121:
122: #ifdef SETJMP
123: extern bool awaiting_input;
124: extern jmp_buf read_interrupt;
125: #endif
126:
127: Hidden Procedure intsig(sig) int sig; { /*sig==SIGINT*/
128: signal(sig, SIG_IGN);
129: int_signal();
130: signal(sig, intsig);
131: #ifdef SETJMP
132: if (awaiting_input) longjmp(read_interrupt, 1);
133: #endif
134: }
135:
136: #ifdef INTEGRATION
137:
138: Visible Procedure bint_interrupt() {
139: signal(SIGINT, intsig);
140: if (interrupted) intsig(SIGINT);
141: }
142:
143: #endif
144:
145: Hidden int(* setsig(sig, func))() int sig, (*func)(); {
146: /*Set a signal, unless it's being ignored*/
147: int (*f)()= signal(sig, SIG_IGN);
148: if (f != SIG_IGN) signal(sig, func);
149: return f;
150: }
151: #endif
152:
153: Visible Procedure initsig() {
154: #ifdef SIGNAL
155: int i;
156: for (i = 1; i<=NSIG; ++i)
157: if (must_handle(i)) VOID setsig(i, burp);
158: #ifndef INTEGRATION
159: if (filtered) {
160: VOID setsig(SIGINT, SIG_IGN);
161: VOID setsig(SIGTRAP, intsig);
162: } else {
163: VOID setsig(SIGINT, intsig);
164: VOID setsig(SIGTRAP, burp);
165: }
166: #else
167: VOID setsig(SIGINT, intsig);
168: #endif
169: VOID setsig(SIGQUIT, aog);
170: VOID setsig(SIGTERM, aog);
171: VOID setsig(SIGFPE, fpe_signal);
172: VOID setsig(SIGPIPE, bye);
173: #endif SIGNAL
174: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.