1*36999Sbostic #include <signal.h> 2*36999Sbostic #include "header.h" /* "Larn is copyrighted 1986 by Noah Morgan.\n" */ 3*36999Sbostic #define BIT(a) (1<<((a)-1)) 4*36999Sbostic extern char savefilename[],wizard,predostuff,nosignal; 5*36999Sbostic static s2choose() /* text to be displayed if ^C during intro screen */ 6*36999Sbostic { 7*36999Sbostic cursor(1,24); lprcat("Press "); setbold(); lprcat("return"); resetbold(); 8*36999Sbostic lprcat(" to continue: "); lflush(); 9*36999Sbostic } 10*36999Sbostic 11*36999Sbostic static cntlc() /* what to do for a ^C */ 12*36999Sbostic { 13*36999Sbostic if (nosignal) return; /* don't do anything if inhibited */ 14*36999Sbostic signal(SIGQUIT,SIG_IGN); signal(SIGINT,SIG_IGN); 15*36999Sbostic quit(); if (predostuff==1) s2choose(); else showplayer(); 16*36999Sbostic lflush(); 17*36999Sbostic signal(SIGQUIT,cntlc); signal(SIGINT,cntlc); 18*36999Sbostic } 19*36999Sbostic 20*36999Sbostic /* 21*36999Sbostic * subroutine to save the game if a hangup signal 22*36999Sbostic */ 23*36999Sbostic static sgam() 24*36999Sbostic { 25*36999Sbostic savegame(savefilename); wizard=1; died(-257); /* hangup signal */ 26*36999Sbostic } 27*36999Sbostic 28*36999Sbostic #ifdef SIGTSTP 29*36999Sbostic static tstop() /* control Y */ 30*36999Sbostic { 31*36999Sbostic if (nosignal) return; /* nothing if inhibited */ 32*36999Sbostic lcreat((char*)0); clearvt100(); lflush(); signal(SIGTSTP,SIG_DFL); 33*36999Sbostic #ifdef SIGVTALRM 34*36999Sbostic /* looks like BSD4.2 or higher - must clr mask for signal to take effect*/ 35*36999Sbostic sigsetmask(sigblock(0)& ~BIT(SIGTSTP)); 36*36999Sbostic #endif 37*36999Sbostic kill(getpid(),SIGTSTP); 38*36999Sbostic 39*36999Sbostic setupvt100(); signal(SIGTSTP,tstop); 40*36999Sbostic if (predostuff==1) s2choose(); else drawscreen(); 41*36999Sbostic showplayer(); lflush(); 42*36999Sbostic } 43*36999Sbostic #endif SIGTSTP 44*36999Sbostic 45*36999Sbostic /* 46*36999Sbostic * subroutine to issue the needed signal traps called from main() 47*36999Sbostic */ 48*36999Sbostic static sigill() { sigpanic(SIGILL); } static sigtrap() { sigpanic(SIGTRAP); } 49*36999Sbostic static sigiot() { sigpanic(SIGIOT); } static sigemt() { sigpanic(SIGEMT); } 50*36999Sbostic static sigfpe() { sigpanic(SIGFPE); } static sigbus() { sigpanic(SIGBUS); } 51*36999Sbostic static sigsegv() { sigpanic(SIGSEGV); } static sigsys() { sigpanic(SIGSYS); } 52*36999Sbostic static sigpipe() { sigpanic(SIGPIPE); } static sigterm() { sigpanic(SIGTERM); } 53*36999Sbostic sigsetup() 54*36999Sbostic { 55*36999Sbostic signal(SIGQUIT, cntlc); signal(SIGINT, cntlc); 56*36999Sbostic signal(SIGKILL, SIG_IGN); signal(SIGHUP, sgam); 57*36999Sbostic signal(SIGILL, sigill); signal(SIGTRAP, sigtrap); 58*36999Sbostic signal(SIGIOT, sigiot); signal(SIGEMT, sigemt); 59*36999Sbostic signal(SIGFPE, sigfpe); signal(SIGBUS, sigbus); 60*36999Sbostic signal(SIGSEGV, sigsegv); signal(SIGSYS, sigsys); 61*36999Sbostic signal(SIGPIPE, sigpipe); signal(SIGTERM, sigterm); 62*36999Sbostic #ifdef SIGTSTP 63*36999Sbostic signal(SIGTSTP,tstop); signal(SIGSTOP,tstop); 64*36999Sbostic #endif SIGTSTP 65*36999Sbostic } 66*36999Sbostic 67*36999Sbostic #ifdef BSD /* for BSD UNIX? */ 68*36999Sbostic 69*36999Sbostic static char *signame[NSIG] = { "", 70*36999Sbostic "SIGHUP", /* 1 hangup */ 71*36999Sbostic "SIGINT", /* 2 interrupt */ 72*36999Sbostic "SIGQUIT", /* 3 quit */ 73*36999Sbostic "SIGILL", /* 4 illegal instruction (not reset when caught) */ 74*36999Sbostic "SIGTRAP", /* 5 trace trap (not reset when caught) */ 75*36999Sbostic "SIGIOT", /* 6 IOT instruction */ 76*36999Sbostic "SIGEMT", /* 7 EMT instruction */ 77*36999Sbostic "SIGFPE", /* 8 floating point exception */ 78*36999Sbostic "SIGKILL", /* 9 kill (cannot be caught or ignored) */ 79*36999Sbostic "SIGBUS", /* 10 bus error */ 80*36999Sbostic "SIGSEGV", /* 11 segmentation violation */ 81*36999Sbostic "SIGSYS", /* 12 bad argument to system call */ 82*36999Sbostic "SIGPIPE", /* 13 write on a pipe with no one to read it */ 83*36999Sbostic "SIGALRM", /* 14 alarm clock */ 84*36999Sbostic "SIGTERM", /* 15 software termination signal from kill */ 85*36999Sbostic "SIGURG", /* 16 urgent condition on IO channel */ 86*36999Sbostic "SIGSTOP", /* 17 sendable stop signal not from tty */ 87*36999Sbostic "SIGTSTP", /* 18 stop signal from tty */ 88*36999Sbostic "SIGCONT", /* 19 continue a stopped process */ 89*36999Sbostic "SIGCHLD", /* 20 to parent on child stop or exit */ 90*36999Sbostic "SIGTTIN", /* 21 to readers pgrp upon background tty read */ 91*36999Sbostic "SIGTTOU", /* 22 like TTIN for output if (tp->t_local<OSTOP) */ 92*36999Sbostic "SIGIO", /* 23 input/output possible signal */ 93*36999Sbostic "SIGXCPU", /* 24 exceeded CPU time limit */ 94*36999Sbostic "SIGXFSZ", /* 25 exceeded file size limit */ 95*36999Sbostic "SIGVTALRM",/* 26 virtual time alarm */ 96*36999Sbostic "SIGPROF", /* 27 profiling time alarm */ 97*36999Sbostic "","","","" }; 98*36999Sbostic 99*36999Sbostic #else BSD /* for system V? */ 100*36999Sbostic 101*36999Sbostic static char *signame[NSIG] = { "", 102*36999Sbostic "SIGHUP", /* 1 hangup */ 103*36999Sbostic "SIGINT", /* 2 interrupt */ 104*36999Sbostic "SIGQUIT", /* 3 quit */ 105*36999Sbostic "SIGILL", /* 4 illegal instruction (not reset when caught) */ 106*36999Sbostic "SIGTRAP", /* 5 trace trap (not reset when caught) */ 107*36999Sbostic "SIGIOT", /* 6 IOT instruction */ 108*36999Sbostic "SIGEMT", /* 7 EMT instruction */ 109*36999Sbostic "SIGFPE", /* 8 floating point exception */ 110*36999Sbostic "SIGKILL", /* 9 kill (cannot be caught or ignored) */ 111*36999Sbostic "SIGBUS", /* 10 bus error */ 112*36999Sbostic "SIGSEGV", /* 11 segmentation violation */ 113*36999Sbostic "SIGSYS", /* 12 bad argument to system call */ 114*36999Sbostic "SIGPIPE", /* 13 write on a pipe with no one to read it */ 115*36999Sbostic "SIGALRM", /* 14 alarm clock */ 116*36999Sbostic "SIGTERM", /* 15 software termination signal from kill */ 117*36999Sbostic "SIGUSR1", /* 16 user defines signal 1 */ 118*36999Sbostic "SIGUSR2", /* 17 user defines signal 2 */ 119*36999Sbostic "SIGCLD", /* 18 child death */ 120*36999Sbostic "SIGPWR", /* 19 power fail */ 121*36999Sbostic "","","","","","","","","","","","" }; 122*36999Sbostic 123*36999Sbostic #endif BSD 124*36999Sbostic 125*36999Sbostic /* 126*36999Sbostic * routine to process a fatal error signal 127*36999Sbostic */ 128*36999Sbostic static sigpanic(sig) 129*36999Sbostic int sig; 130*36999Sbostic { 131*36999Sbostic char buf[128]; 132*36999Sbostic signal(sig,SIG_DFL); 133*36999Sbostic sprintf(buf,"\nLarn - Panic! Signal %d received [%s]",sig,signame[sig]); 134*36999Sbostic write(2,buf,strlen(buf)); sleep(2); 135*36999Sbostic sncbr(); 136*36999Sbostic savegame(savefilename); 137*36999Sbostic kill(getpid(),sig); /* this will terminate us */ 138*36999Sbostic } 139