File:
[gforth] /
gforth /
Attic /
io.c
Revision
1.8:
download - view:
text,
annotated -
select for diffs
Mon Mar 13 09:17:29 1995 UTC (28 years, 2 months ago) by
anton
Branches:
MAIN
CVS tags:
HEAD
Added stuff for documenting Forth source and integrating it into the texi file
changed checks for DOMAINOS to checks for apollo (which is defined on apollos)
changed "-evaluate" (which did not work anyway) to "--evaluate"
added debugging.fs and assert.fs to startup.fs
1: /* direct key io driver
2:
3: The following is stolen from the readline library for bash
4: */
5:
6: /*
7: Use -D_POSIX_VERSION for POSIX systems.
8: */
9:
10: #include <unistd.h>
11:
12: #ifdef apollo
13: #define _POSIX_VERSION
14: #endif
15:
16: #include <stdio.h>
17: #include <signal.h>
18: #include <sys/types.h>
19: #ifndef apollo
20: #include <sys/ioctl.h>
21: #endif
22: #include <fcntl.h>
23: #include <sys/file.h>
24: #include <setjmp.h>
25: #include "forth.h"
26: #include "io.h"
27:
28: #if defined (__GNUC__)
29: # define alloca __builtin_alloca
30: #else
31: # if defined (sparc) || defined (HAVE_ALLOCA_H)
32: # include <alloca.h>
33: # endif
34: #endif
35:
36: #define NEW_TTY_DRIVER
37: #define HAVE_BSD_SIGNALS
38: /*
39: #ifndef apollo
40: #define USE_XON_XOFF
41: #endif
42: */
43:
44: #define HANDLE_SIGNALS
45:
46: /* Some USG machines have BSD signal handling (sigblock, sigsetmask, etc.) */
47: #if defined (USG) && !defined (hpux)
48: #undef HAVE_BSD_SIGNALS
49: #endif
50:
51: /* System V machines use termio. */
52: #if !defined (_POSIX_VERSION)
53: # if defined (USG) || defined (hpux) || defined (Xenix) || defined (sgi) || defined (DGUX) || defined (ultrix) || defined (Solaris)
54: # undef NEW_TTY_DRIVER
55: # define TERMIO_TTY_DRIVER
56: # include <termio.h>
57: # if !defined (TCOON)
58: # define TCOON 1
59: # endif
60: # endif /* USG || hpux || Xenix || sgi || DUGX || ultrix*/
61: #endif /* !_POSIX_VERSION */
62:
63: /* Posix systems use termios and the Posix signal functions. */
64: #if defined (_POSIX_VERSION)
65: # if !defined (TERMIOS_MISSING)
66: # undef NEW_TTY_DRIVER
67: # define TERMIOS_TTY_DRIVER
68: # include <termios.h>
69: # endif /* !TERMIOS_MISSING */
70: # define HAVE_POSIX_SIGNALS
71: # if !defined (O_NDELAY)
72: # define O_NDELAY O_NONBLOCK /* Posix-style non-blocking i/o */
73: # endif /* O_NDELAY */
74: #endif /* _POSIX_VERSION */
75:
76: /* Other (BSD) machines use sgtty. */
77: #if defined (NEW_TTY_DRIVER)
78: #include <sgtty.h>
79: #endif
80:
81: /* Define _POSIX_VDISABLE if we are not using the `new' tty driver and
82: it is not already defined. It is used both to determine if a
83: special character is disabled and to disable certain special
84: characters. Posix systems should set to 0, USG systems to -1. */
85: #if !defined (NEW_TTY_DRIVER) && !defined (_POSIX_VDISABLE)
86: # if defined (_POSIX_VERSION)
87: # define _POSIX_VDISABLE 0
88: # else /* !_POSIX_VERSION */
89: # define _POSIX_VDISABLE -1
90: # endif /* !_POSIX_VERSION */
91: #endif /* !NEW_TTY_DRIVER && !_POSIX_VDISABLE */
92:
93: #include <errno.h>
94: extern int errno;
95:
96: #if defined (SHELL)
97: # include <posixstat.h>
98: #else
99: # include <sys/stat.h>
100: #endif /* !SHELL */
101: /* #define HACK_TERMCAP_MOTION */
102:
103: #if defined (USG) && defined (hpux)
104: # if !defined (USGr3)
105: # define USGr3
106: # endif /* USGr3 */
107: #endif /* USG && hpux */
108:
109: #if (defined (_POSIX_VERSION) || defined (USGr3)) && !defined(apollo)
110: # include <dirent.h>
111: # define direct dirent
112: # if defined (_POSIX_VERSION)
113: # define D_NAMLEN(d) (strlen ((d)->d_name))
114: # else /* !_POSIX_VERSION */
115: # define D_NAMLEN(d) ((d)->d_reclen)
116: # endif /* !_POSIX_VERSION */
117: #else /* !_POSIX_VERSION && !USGr3 */
118: # define D_NAMLEN(d) ((d)->d_namlen)
119: # if !defined (USG)
120: # include <sys/dir.h>
121: # else /* USG */
122: # if defined (Xenix)
123: # include <sys/ndir.h>
124: # else /* !Xenix */
125: # include <ndir.h>
126: # endif /* !Xenix */
127: # endif /* USG */
128: #endif /* !POSIX_VERSION && !USGr3 */
129:
130: #if defined (USG) && defined (TIOCGWINSZ)
131: # include <sys/stream.h>
132: # if defined (USGr4) || defined (USGr3)
133: # if defined (Symmetry) || defined (_SEQUENT_)
134: # include <sys/pte.h>
135: # else
136: # include <sys/ptem.h>
137: # endif /* !Symmetry || _SEQUENT_ */
138: # endif /* USGr4 */
139: #endif /* USG && TIOCGWINSZ */
140:
141: #if defined (TERMIOS_TTY_DRIVER)
142: static struct termios otio;
143: #else
144: static struct termio otio;
145: #endif /* !TERMIOS_TTY_DRIVER */
146:
147: /* Non-zero means echo characters as they are read. */
148: int readline_echoing_p = 1;
149:
150: /* The character that can generate an EOF. Really read from
151: the terminal driver... just defaulted here. */
152:
153: #ifndef CTRL
154: #define CTRL(key) ((key)-'@')
155: #endif
156:
157: static int eof_char = CTRL ('D');
158:
159: /* **************************************************************** */
160: /* */
161: /* Saving and Restoring the TTY */
162: /* */
163: /* **************************************************************** */
164:
165: /* Non-zero means that the terminal is in a prepped state. */
166: static int terminal_prepped = 0;
167:
168: #if defined (NEW_TTY_DRIVER)
169:
170: /* Standard flags, including ECHO. */
171: static int original_tty_flags = 0;
172:
173: /* Local mode flags, like LPASS8. */
174: static int local_mode_flags = 0;
175:
176: /* Terminal characters. This has C-s and C-q in it. */
177: static struct tchars original_tchars;
178:
179: /* Local special characters. This has the interrupt characters in it. */
180: #if defined (TIOCGLTC)
181: static struct ltchars original_ltchars;
182: #endif
183:
184: /* Bind KEY to FUNCTION. Returns non-zero if KEY is out of range. */
185:
186: #if defined (TIOCGETC)
187: #if defined (USE_XON_XOFF)
188:
189: int
190: bind_key (key, function)
191: int key;
192: Function *function;
193: {
194: if (key < 0)
195: return (key);
196:
197: if (key > 127 && key < 256)
198: {
199: if (keymap[ESC].type == ISKMAP)
200: {
201: Keymap escmap = (Keymap)keymap[ESC].function;
202:
203: key -= 128;
204: escmap[key].type = ISFUNC;
205: escmap[key].function = function;
206: return (0);
207: }
208: return (key);
209: }
210:
211: keymap[key].type = ISFUNC;
212: keymap[key].function = function;
213: return (0);
214: }
215: #endif
216: #endif
217:
218: /* We use this to get and set the tty_flags. */
219: static struct sgttyb the_ttybuff;
220:
221: #if defined (USE_XON_XOFF)
222: /* If the terminal was in xoff state when we got to it, then xon_char
223: contains the character that is supposed to start it again. */
224: static int xon_char, xoff_state;
225: #endif /* USE_XON_XOFF */
226:
227: /* **************************************************************** */
228: /* */
229: /* Bogus Flow Control */
230: /* */
231: /* **************************************************************** */
232:
233: restart_output (count, key)
234: int count, key;
235: {
236: int fildes = fileno (stdin);
237: #if defined (TIOCSTART)
238: #if defined (apollo)
239: ioctl (&fildes, TIOCSTART, 0);
240: #else
241: ioctl (fildes, TIOCSTART, 0);
242: #endif /* apollo */
243:
244: #else
245: # if defined (TERMIOS_TTY_DRIVER)
246: tcflow (fildes, TCOON);
247: # else
248: # if defined (TCXONC)
249: ioctl (fildes, TCXONC, TCOON);
250: # endif /* TCXONC */
251: # endif /* !TERMIOS_TTY_DRIVER */
252: #endif /* TIOCSTART */
253: }
254:
255: /* Put the terminal in CBREAK mode so that we can detect key presses. */
256: void prep_terminal ()
257: {
258: int tty = fileno (stdin);
259: #if defined (HAVE_BSD_SIGNALS)
260: int oldmask;
261: #endif /* HAVE_BSD_SIGNALS */
262:
263: if (terminal_prepped)
264: return;
265:
266: oldmask = sigblock (sigmask (SIGINT));
267:
268: /* We always get the latest tty values. Maybe stty changed them. */
269: ioctl (tty, TIOCGETP, &the_ttybuff);
270: original_tty_flags = the_ttybuff.sg_flags;
271:
272: readline_echoing_p = (original_tty_flags & ECHO);
273:
274: #if defined (TIOCLGET)
275: ioctl (tty, TIOCLGET, &local_mode_flags);
276: #endif
277:
278: #if !defined (ANYP)
279: # define ANYP (EVENP | ODDP)
280: #endif
281:
282: /* If this terminal doesn't care how the 8th bit is used,
283: then we can use it for the meta-key. We check by seeing
284: if BOTH odd and even parity are allowed. */
285: if (the_ttybuff.sg_flags & ANYP)
286: {
287: #if defined (PASS8)
288: the_ttybuff.sg_flags |= PASS8;
289: #endif
290:
291: /* Hack on local mode flags if we can. */
292: #if defined (TIOCLGET) && defined (LPASS8)
293: {
294: int flags;
295: flags = local_mode_flags | LPASS8;
296: ioctl (tty, TIOCLSET, &flags);
297: }
298: #endif /* TIOCLGET && LPASS8 */
299: }
300:
301: #if defined (TIOCGETC)
302: {
303: struct tchars temp;
304:
305: ioctl (tty, TIOCGETC, &original_tchars);
306: temp = original_tchars;
307:
308: #if defined (USE_XON_XOFF)
309: /* Get rid of C-s and C-q.
310: We remember the value of startc (C-q) so that if the terminal is in
311: xoff state, the user can xon it by pressing that character. */
312: xon_char = temp.t_startc;
313: temp.t_stopc = -1;
314: temp.t_startc = -1;
315:
316: /* If there is an XON character, bind it to restart the output. */
317: if (xon_char != -1)
318: bind_key (xon_char, restart_output);
319: #endif /* USE_XON_XOFF */
320:
321: /* If there is an EOF char, bind eof_char to it. */
322: if (temp.t_eofc != -1)
323: eof_char = temp.t_eofc;
324:
325: #if defined (NO_KILL_INTR)
326: /* Get rid of C-\ and C-c. */
327: temp.t_intrc = temp.t_quitc = -1;
328: #endif /* NO_KILL_INTR */
329:
330: ioctl (tty, TIOCSETC, &temp);
331: }
332: #endif /* TIOCGETC */
333:
334: #if defined (TIOCGLTC)
335: {
336: struct ltchars temp;
337:
338: ioctl (tty, TIOCGLTC, &original_ltchars);
339: temp = original_ltchars;
340:
341: /* Make the interrupt keys go away. Just enough to make people
342: happy. */
343: temp.t_dsuspc = -1; /* C-y */
344: temp.t_lnextc = -1; /* C-v */
345:
346: ioctl (tty, TIOCSLTC, &temp);
347: }
348: #endif /* TIOCGLTC */
349:
350: the_ttybuff.sg_flags &= ~(ECHO | CRMOD);
351: the_ttybuff.sg_flags |= CBREAK;
352: ioctl (tty, TIOCSETN, &the_ttybuff);
353:
354: terminal_prepped = 1;
355:
356: #if defined (HAVE_BSD_SIGNALS)
357: sigsetmask (oldmask);
358: #endif
359: }
360:
361: /* Restore the terminal to its original state. */
362: void deprep_terminal ()
363: {
364: int tty = fileno (stdin);
365: #if defined (HAVE_BSD_SIGNALS)
366: int oldmask;
367: #endif
368:
369: if (!terminal_prepped)
370: return;
371:
372: oldmask = sigblock (sigmask (SIGINT));
373:
374: the_ttybuff.sg_flags = original_tty_flags;
375: ioctl (tty, TIOCSETN, &the_ttybuff);
376: readline_echoing_p = 1;
377:
378: #if defined (TIOCLGET)
379: ioctl (tty, TIOCLSET, &local_mode_flags);
380: #endif
381:
382: #if defined (TIOCSLTC)
383: ioctl (tty, TIOCSLTC, &original_ltchars);
384: #endif
385:
386: #if defined (TIOCSETC)
387: ioctl (tty, TIOCSETC, &original_tchars);
388: #endif
389: terminal_prepped = 0;
390:
391: #if defined (HAVE_BSD_SIGNALS)
392: sigsetmask (oldmask);
393: #endif
394: }
395:
396: #else /* !defined (NEW_TTY_DRIVER) */
397:
398: #if !defined (VMIN)
399: #define VMIN VEOF
400: #endif
401:
402: #if !defined (VTIME)
403: #define VTIME VEOL
404: #endif
405:
406: void prep_terminal ()
407: {
408: int tty = fileno (stdin);
409: #if defined (TERMIOS_TTY_DRIVER)
410: struct termios tio;
411: #else
412: struct termio tio;
413: #endif /* !TERMIOS_TTY_DRIVER */
414:
415: #if defined (HAVE_POSIX_SIGNALS)
416: sigset_t set, oset;
417: #else
418: # if defined (HAVE_BSD_SIGNALS)
419: int oldmask;
420: # endif /* HAVE_BSD_SIGNALS */
421: #endif /* !HAVE_POSIX_SIGNALS */
422:
423: if (terminal_prepped)
424: return;
425:
426: /* Try to keep this function from being INTerrupted. We can do it
427: on POSIX and systems with BSD-like signal handling. */
428: #if defined (HAVE_POSIX_SIGNALS)
429: sigemptyset (&set);
430: sigemptyset (&oset);
431: sigaddset (&set, SIGINT);
432: sigprocmask (SIG_BLOCK, &set, &oset);
433: #else /* !HAVE_POSIX_SIGNALS */
434: # if defined (HAVE_BSD_SIGNALS)
435: oldmask = sigblock (sigmask (SIGINT));
436: # endif /* HAVE_BSD_SIGNALS */
437: #endif /* !HAVE_POSIX_SIGNALS */
438:
439: #if defined (TERMIOS_TTY_DRIVER)
440: tcgetattr (tty, &tio);
441: #else
442: ioctl (tty, TCGETA, &tio);
443: #endif /* !TERMIOS_TTY_DRIVER */
444:
445: otio = tio;
446:
447: readline_echoing_p = (tio.c_lflag & ECHO);
448:
449: tio.c_lflag &= ~(ICANON | ECHO);
450:
451: if (otio.c_cc[VEOF] != _POSIX_VDISABLE)
452: eof_char = otio.c_cc[VEOF];
453:
454: #if defined (USE_XON_XOFF)
455: #if defined (IXANY)
456: tio.c_iflag &= ~(IXON | IXOFF | IXANY);
457: #else
458: /* `strict' Posix systems do not define IXANY. */
459: tio.c_iflag &= ~(IXON | IXOFF);
460: #endif /* IXANY */
461: #endif /* USE_XON_XOFF */
462:
463: /* Only turn this off if we are using all 8 bits. */
464: if ((tio.c_cflag & CSIZE) == CS8)
465: tio.c_iflag &= ~(ISTRIP | INPCK);
466:
467: /* Make sure we differentiate between CR and NL on input. */
468: tio.c_iflag &= ~(ICRNL | INLCR);
469:
470: #if !defined (HANDLE_SIGNALS)
471: tio.c_lflag &= ~ISIG;
472: #else
473: tio.c_lflag |= ISIG;
474: #endif
475:
476: tio.c_cc[VMIN] = 1;
477: tio.c_cc[VTIME] = 0;
478:
479: /* Turn off characters that we need on Posix systems with job control,
480: just to be sure. This includes ^Y and ^V. This should not really
481: be necessary. */
482: #if defined (TERMIOS_TTY_DRIVER) && defined (_POSIX_JOB_CONTROL)
483:
484: #if defined (VLNEXT)
485: tio.c_cc[VLNEXT] = _POSIX_VDISABLE;
486: #endif
487:
488: #if defined (VDSUSP)
489: tio.c_cc[VDSUSP] = _POSIX_VDISABLE;
490: #endif
491:
492: #endif /* POSIX && JOB_CONTROL */
493:
494: #if defined (TERMIOS_TTY_DRIVER)
495: tcsetattr (tty, TCSADRAIN, &tio);
496: tcflow (tty, TCOON); /* Simulate a ^Q. */
497: #else
498: ioctl (tty, TCSETAW, &tio);
499: ioctl (tty, TCXONC, 1); /* Simulate a ^Q. */
500: #endif /* !TERMIOS_TTY_DRIVER */
501:
502: terminal_prepped = 1;
503:
504: #if defined (HAVE_POSIX_SIGNALS)
505: sigprocmask (SIG_SETMASK, &oset, (sigset_t *)NULL);
506: #else
507: # if defined (HAVE_BSD_SIGNALS)
508: sigsetmask (oldmask);
509: # endif /* HAVE_BSD_SIGNALS */
510: #endif /* !HAVE_POSIX_SIGNALS */
511: }
512:
513: void deprep_terminal ()
514: {
515: int tty = fileno (stdin);
516:
517: /* Try to keep this function from being INTerrupted. We can do it
518: on POSIX and systems with BSD-like signal handling. */
519: #if defined (HAVE_POSIX_SIGNALS)
520: sigset_t set, oset;
521: #else /* !HAVE_POSIX_SIGNALS */
522: # if defined (HAVE_BSD_SIGNALS)
523: int oldmask;
524: # endif /* HAVE_BSD_SIGNALS */
525: #endif /* !HAVE_POSIX_SIGNALS */
526:
527: if (!terminal_prepped)
528: return;
529:
530: #if defined (HAVE_POSIX_SIGNALS)
531: sigemptyset (&set);
532: sigemptyset (&oset);
533: sigaddset (&set, SIGINT);
534: sigprocmask (SIG_BLOCK, &set, &oset);
535: #else /* !HAVE_POSIX_SIGNALS */
536: # if defined (HAVE_BSD_SIGNALS)
537: oldmask = sigblock (sigmask (SIGINT));
538: # endif /* HAVE_BSD_SIGNALS */
539: #endif /* !HAVE_POSIX_SIGNALS */
540:
541: #if defined (TERMIOS_TTY_DRIVER)
542: tcsetattr (tty, TCSADRAIN, &otio);
543: tcflow (tty, TCOON); /* Simulate a ^Q. */
544: #else /* TERMIOS_TTY_DRIVER */
545: ioctl (tty, TCSETAW, &otio);
546: ioctl (tty, TCXONC, 1); /* Simulate a ^Q. */
547: #endif /* !TERMIOS_TTY_DRIVER */
548:
549: terminal_prepped = 0;
550:
551: #if defined (HAVE_POSIX_SIGNALS)
552: sigprocmask (SIG_SETMASK, &oset, (sigset_t *)NULL);
553: #else /* !HAVE_POSIX_SIGNALS */
554: # if defined (HAVE_BSD_SIGNALS)
555: sigsetmask (oldmask);
556: # endif /* HAVE_BSD_SIGNALS */
557: #endif /* !HAVE_POSIX_SIGNALS */
558: }
559: #endif /* NEW_TTY_DRIVER */
560:
561: /* If a character is available to be read, then read it
562: and stuff it into IBUFFER. Otherwise, just return. */
563:
564: long pending = -1L;
565:
566: long key_avail (stream)
567: FILE *stream;
568: {
569: int tty = fileno (stream);
570: long chars_avail = pending;
571: int result;
572:
573: #if defined (FIONREAD)
574: result = ioctl (tty, FIONREAD, &chars_avail);
575: #endif
576:
577: if(chars_avail == -1L)
578: { unsigned char inchar;
579:
580: fcntl(tty, F_SETFL, O_NDELAY);
581: result = read(tty, &inchar, sizeof(char));
582: if(result == sizeof(char))
583: {
584: chars_avail = 1;
585: pending = (long)inchar;
586: }
587: else
588: chars_avail = 0;
589: fcntl(tty, F_SETFL, 0);
590: }
591:
592: return chars_avail;
593: }
594:
595: /* Get a key from the buffer of characters to be read.
596: Return the key in KEY.
597: Result is KEY if there was a key, or 0 if there wasn't. */
598:
599: /* When compiling and running in the `Posix' environment, Ultrix does
600: not restart system calls, so this needs to do it. */
601:
602: unsigned char getkey(stream)
603: FILE *stream;
604: {
605: int result;
606: unsigned char c;
607:
608: while (pending < 0)
609: {
610: result = read (fileno (stream), &c, sizeof (char));
611:
612: if (result == sizeof (char))
613: return /* (c == 0x7F ? 0x08 :*/ c /*)*/;
614:
615: /* If zero characters are returned, then the file that we are
616: reading from is empty! Return EOF in that case. */
617: if (result == 0)
618: return (0);
619:
620: /* If the error that we received was SIGINT, then try again,
621: this is simply an interrupted system call to read ().
622: Otherwise, some error ocurred, also signifying EOF. */
623: if (errno != EINTR)
624: return (EOF);
625: }
626:
627: result = (int) pending;
628: pending = -1L;
629:
630: return result;
631: }
632:
633: #ifdef TEST
634:
635: #include <time.h>
636:
637: int timewait=100000;
638:
639: int main()
640: {
641: unsigned char c;
642:
643: prep_terminal();
644:
645: do
646: {
647: int i=0;
648:
649: while(!key_avail(stdin))
650: {
651: printf("%04d",i);
652: fflush(stdout);
653: {
654: struct timeval timeout;
655: timeout.tv_sec=timewait/1000000;
656: timeout.tv_usec=timewait%1000000;
657: (void)select(0,0,0,0,&timeout);
658: }
659: i++;
660: printf("\b\b\b\b");
661: fflush(stdout);
662: }
663: c = getkey(stdin);
664: printf("%02x,",(int)c);
665: fflush(stdout);
666: } while(c != 0x1B);
667:
668: deprep_terminal();
669: puts("");
670: }
671: #endif
672:
673: /* signal handling taken from pfe by Dirk Zoller (Copylefted) - anton */
674: /* !! needs cleanup */
675: char *
676: sigmsg (int sig)
677: {
678: static char buf [25];
679: static char *msg [] =
680: {
681: "Hangup", /* These strings are cited from */
682: "Interrupt", /* Rochkind: Advanced UNIX programming */
683: "Quit",
684: "Illegal Instruction",
685: "Trace Trap",
686: "IOT instruction",
687: "EMT instruction",
688: "Floating point exception",
689: "Kill",
690: "Bus error",
691: "Segmentation Violation",
692: "Bad arg to system call",
693: "Broken pipe",
694: "Alarm clock",
695: "Terminate signal",
696: "User signal 1",
697: "User signal 2",
698: };
699:
700: if ((unsigned)sig <= 17)
701: return msg [sig - 1];
702: sprintf (buf, "signal %d received", sig);
703: return buf;
704: }
705:
706: static void
707: graceful_exit (int sig)
708: {
709: deprep_terminal();
710: if ((unsigned)sig <= 17)
711: fprintf (stderr, "\n\n%s.\n", sigmsg (sig));
712: else
713: fprintf (stderr, "\n\nSignal %d received, terminated.\n", sig);
714: exit (0x80|sig);
715: }
716:
717: jmp_buf throw_jmp_buf;
718:
719: static void
720: signal_throw(int sig)
721: {
722: static int throw_codes[] = {
723: -256,
724: -28,
725: -257,
726: -258,
727: -259,
728: -260,
729: -261,
730: -55,
731: -262,
732: -23,
733: -9,
734: -263,
735: -264,
736: -265,
737: -266,
738: -267,
739: -268,
740: };
741: signal(sig,signal_throw);
742: longjmp(throw_jmp_buf,throw_codes[sig-1]); /* or use siglongjmp ? */
743: }
744:
745: static void
746: termprep (int sig)
747: {
748: terminal_prepped=0; prep_terminal();
749: signal(sig,termprep);
750: }
751:
752: void
753: install_signal_handlers (void)
754: {
755: /* !! These definitions seem to be system dependent
756: We could have them in the machine.h file,
757: but I would like something more automatic - anton */
758: #define SIGS_TO_IGNORE SIGCHLD
759: #define SIGS_TO_ABORT SIGINT, SIGILL, SIGFPE, SIGUSR1, SIGSEGV, SIGUSR2, \
760: SIGALRM, SIGBUS
761: #define SIGS_TO_QUIT SIGHUP, SIGQUIT, SIGABRT, SIGPIPE, \
762: SIGTERM
763: #define SIGS_TO_TERMPREP SIGCONT
764:
765: static short sigs_to_ignore [] = { SIGS_TO_IGNORE };
766: static short sigs_to_abort [] = { SIGS_TO_ABORT };
767: static short sigs_to_quit [] = { SIGS_TO_QUIT };
768: static short sigs_to_termprep [] = { SIGS_TO_TERMPREP };
769: int i;
770:
771: #define DIM(X) (sizeof (X) / sizeof *(X))
772: for (i = 0; i < DIM (sigs_to_ignore); i++)
773: if (sigs_to_ignore [i])
774: signal (sigs_to_ignore [i], SIG_IGN);
775: for (i = 0; i < DIM (sigs_to_abort); i++)
776: signal (sigs_to_abort [i], signal_throw); /* !! change to throw */
777: for (i = 0; i < DIM (sigs_to_quit); i++)
778: signal (sigs_to_quit [i], graceful_exit);
779: for (i = 0; i < DIM (sigs_to_termprep); i++)
780: signal (sigs_to_termprep [i], termprep);
781: }
782: /* end signal handling */
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>