10Sstevel@tonic-gate /* 20Sstevel@tonic-gate * CDDL HEADER START 30Sstevel@tonic-gate * 40Sstevel@tonic-gate * The contents of this file are subject to the terms of the 50Sstevel@tonic-gate * Common Development and Distribution License, Version 1.0 only 60Sstevel@tonic-gate * (the "License"). You may not use this file except in compliance 70Sstevel@tonic-gate * with the License. 80Sstevel@tonic-gate * 90Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 100Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing. 110Sstevel@tonic-gate * See the License for the specific language governing permissions 120Sstevel@tonic-gate * and limitations under the License. 130Sstevel@tonic-gate * 140Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each 150Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 160Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the 170Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying 180Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner] 190Sstevel@tonic-gate * 200Sstevel@tonic-gate * CDDL HEADER END 210Sstevel@tonic-gate */ 220Sstevel@tonic-gate /* 230Sstevel@tonic-gate * Copyright 1996 Sun Microsystems, Inc. All rights reserved. 240Sstevel@tonic-gate * Use is subject to license terms. 250Sstevel@tonic-gate */ 260Sstevel@tonic-gate 27*722Smuffin #pragma ident "%Z%%M% %I% %E% SMI" 280Sstevel@tonic-gate 290Sstevel@tonic-gate #include "signalmap.h" 300Sstevel@tonic-gate #include <sys/signal.h> 310Sstevel@tonic-gate #include <sys/errno.h> 320Sstevel@tonic-gate 330Sstevel@tonic-gate extern int errno; 340Sstevel@tonic-gate void (*handlers[32])(); /* XXX - 32??? NSIG, maybe? */ 350Sstevel@tonic-gate 36*722Smuffin void 37*722Smuffin maphandler(int sig, int code, struct sigcontext *scp, char *addr) 380Sstevel@tonic-gate { 390Sstevel@tonic-gate switch (sig) { 400Sstevel@tonic-gate case SIGBUS: 410Sstevel@tonic-gate case SIGSEGV: 420Sstevel@tonic-gate switch (FC_CODE(code)) { 430Sstevel@tonic-gate case 3: /* 5.x value for FC_OBJERR */ 440Sstevel@tonic-gate code = FC_MAKE_ERR(FC_ERRNO(code)); 450Sstevel@tonic-gate break; 460Sstevel@tonic-gate case 5: /* 5.x value for FC_NOMAP */ 470Sstevel@tonic-gate code = FC_NOMAP; 480Sstevel@tonic-gate break; 490Sstevel@tonic-gate } 500Sstevel@tonic-gate break; 510Sstevel@tonic-gate } 520Sstevel@tonic-gate __sendsig(maptooldsig(sig), code, scp, addr, handlers[sig]); 530Sstevel@tonic-gate } 540Sstevel@tonic-gate 55*722Smuffin void (* 56*722Smuffin signal(int sig, void (*a)(int)))(int) 570Sstevel@tonic-gate { 580Sstevel@tonic-gate int newsig; 590Sstevel@tonic-gate 600Sstevel@tonic-gate struct sigvec osv, sv; 610Sstevel@tonic-gate 620Sstevel@tonic-gate sv.sv_handler = a; 630Sstevel@tonic-gate sv.sv_mask = 0; 640Sstevel@tonic-gate #ifdef S5EMUL 650Sstevel@tonic-gate sv.sv_flags = SV_INTERRUPT|SV_RESETHAND; 660Sstevel@tonic-gate #else 670Sstevel@tonic-gate sv.sv_flags = 0; 680Sstevel@tonic-gate #endif 690Sstevel@tonic-gate if (sigvec(sig, &sv, &osv) < 0) 700Sstevel@tonic-gate return (BADSIG); 710Sstevel@tonic-gate return (osv.sv_handler); 720Sstevel@tonic-gate } 730Sstevel@tonic-gate 740Sstevel@tonic-gate 75*722Smuffin int 76*722Smuffin sigvec(int sig, struct sigvec *nvec, struct sigvec *ovec) 770Sstevel@tonic-gate { 780Sstevel@tonic-gate int newsig; 790Sstevel@tonic-gate struct sigvec tvec, *tvecp; 80*722Smuffin void (*oldhand)(int); 810Sstevel@tonic-gate 820Sstevel@tonic-gate if ((int)nvec == -1 || (int)ovec == -1) { 830Sstevel@tonic-gate errno = EFAULT; 840Sstevel@tonic-gate return (-1); 850Sstevel@tonic-gate } 860Sstevel@tonic-gate 870Sstevel@tonic-gate newsig = maptonewsig(sig); 880Sstevel@tonic-gate oldhand = handlers[newsig]; 890Sstevel@tonic-gate 900Sstevel@tonic-gate if ((tvecp = nvec) != 0) { 910Sstevel@tonic-gate tvec = *nvec; 920Sstevel@tonic-gate tvecp = &tvec; 930Sstevel@tonic-gate /* 940Sstevel@tonic-gate * To be compatible with the behavior of SunOS 4.x: 950Sstevel@tonic-gate * If the new signal handler is SIG_IGN or SIG_DFL, 960Sstevel@tonic-gate * do not change the signal's entry in the handler array. 970Sstevel@tonic-gate * This allows a child of vfork(2) to set signal handlers 980Sstevel@tonic-gate * to SIG_IGN or SIG_DFL without affecting the parent. 990Sstevel@tonic-gate */ 1000Sstevel@tonic-gate if (tvecp->sv_handler != SIG_DFL && 1010Sstevel@tonic-gate tvecp->sv_handler != SIG_IGN) { 1020Sstevel@tonic-gate handlers[newsig] = tvecp->sv_handler; 1030Sstevel@tonic-gate tvecp->sv_handler = maphandler; 1040Sstevel@tonic-gate } 1050Sstevel@tonic-gate } 1060Sstevel@tonic-gate 1070Sstevel@tonic-gate if (ucbsigvec(newsig, tvecp, ovec) == -1) { 1080Sstevel@tonic-gate handlers[newsig] = oldhand; 1090Sstevel@tonic-gate return (-1); 1100Sstevel@tonic-gate } 1110Sstevel@tonic-gate 1120Sstevel@tonic-gate if (ovec && ovec->sv_handler != SIG_DFL && ovec->sv_handler != SIG_IGN) 1130Sstevel@tonic-gate ovec->sv_handler = oldhand; 1140Sstevel@tonic-gate 1150Sstevel@tonic-gate return (0); 1160Sstevel@tonic-gate } 1170Sstevel@tonic-gate 118*722Smuffin int 119*722Smuffin sigsetmask(int mask) 1200Sstevel@tonic-gate { 1210Sstevel@tonic-gate int ret; 1220Sstevel@tonic-gate ret = ucbsigsetmask(maptonewmask(mask)); 123*722Smuffin return (maptooldmask(ret)); 1240Sstevel@tonic-gate } 1250Sstevel@tonic-gate 126*722Smuffin int 127*722Smuffin sigblock(int mask) 1280Sstevel@tonic-gate { 1290Sstevel@tonic-gate int ret; 1300Sstevel@tonic-gate ret = ucbsigblock(maptonewmask(mask)); 131*722Smuffin return (maptooldmask(ret)); 1320Sstevel@tonic-gate } 1330Sstevel@tonic-gate 1340Sstevel@tonic-gate 135*722Smuffin int 136*722Smuffin sigpause(int mask) 1370Sstevel@tonic-gate { 1380Sstevel@tonic-gate int ret; 139*722Smuffin return (ucbsigpause(maptonewmask(mask))); 1400Sstevel@tonic-gate } 1410Sstevel@tonic-gate 142*722Smuffin int 143*722Smuffin siginterrupt(int sig, int flag) 1440Sstevel@tonic-gate { 145*722Smuffin return (ucbsiginterrupt(maptonewsig(sig), flag)); 1460Sstevel@tonic-gate } 1470Sstevel@tonic-gate 1480Sstevel@tonic-gate 149*722Smuffin int 150*722Smuffin maptonewsig(int sig) 1510Sstevel@tonic-gate { 1520Sstevel@tonic-gate switch (sig) { 1530Sstevel@tonic-gate case SIGURG: /* urgent condition on IO channel */ 154*722Smuffin return (XSIGURG); 1550Sstevel@tonic-gate case SIGSTOP: /* sendable stop signal not from tty */ 156*722Smuffin return (XSIGSTOP); 1570Sstevel@tonic-gate case SIGTSTP: /* stop signal from tty */ 158*722Smuffin return (XSIGTSTP); 1590Sstevel@tonic-gate case SIGCONT: /* continue a stopped process */ 160*722Smuffin return (XSIGCONT); 1610Sstevel@tonic-gate case SIGCLD: /* System V name for SIGCHLD */ 162*722Smuffin return (XSIGCLD); 1630Sstevel@tonic-gate case SIGTTIN: /* to readers pgrp upon background tty read */ 164*722Smuffin return (XSIGTTIN); 1650Sstevel@tonic-gate case SIGTTOU: /* like TTIN for output */ 166*722Smuffin return (XSIGTTOU); 1670Sstevel@tonic-gate case SIGIO: /* input/output possible signal */ 168*722Smuffin return (XSIGIO); 1690Sstevel@tonic-gate case SIGXCPU: /* exceeded CPU time limit */ 170*722Smuffin return (XSIGXCPU); 1710Sstevel@tonic-gate case SIGXFSZ: /* exceeded file size limit */ 172*722Smuffin return (XSIGXFSZ); 1730Sstevel@tonic-gate case SIGVTALRM: /* virtual time alarm */ 174*722Smuffin return (XSIGVTALRM); 1750Sstevel@tonic-gate case SIGPROF: /* profiling time alarm */ 176*722Smuffin return (XSIGPROF); 1770Sstevel@tonic-gate case SIGWINCH: /* window changed */ 178*722Smuffin return (XSIGWINCH); 1790Sstevel@tonic-gate case SIGLOST: /* resource lost, not supported */ 180*722Smuffin return (-1); 1810Sstevel@tonic-gate case SIGUSR1: 182*722Smuffin return (XSIGUSR1); 1830Sstevel@tonic-gate case SIGUSR2: /* user defined signal 2 */ 184*722Smuffin return (XSIGUSR2); 1850Sstevel@tonic-gate default: 186*722Smuffin return (sig); 1870Sstevel@tonic-gate } 1880Sstevel@tonic-gate } 1890Sstevel@tonic-gate 190*722Smuffin int 191*722Smuffin maptooldsig(int sig) 1920Sstevel@tonic-gate { 1930Sstevel@tonic-gate switch (sig) { 1940Sstevel@tonic-gate case XSIGURG: /* urgent condition on IO channel */ 195*722Smuffin return (SIGURG); 1960Sstevel@tonic-gate case XSIGSTOP: /* sendable stop signal not from tty */ 197*722Smuffin return (SIGSTOP); 1980Sstevel@tonic-gate case XSIGTSTP: /* stop signal from tty */ 199*722Smuffin return (SIGTSTP); 2000Sstevel@tonic-gate case XSIGCONT: /* continue a stopped process */ 201*722Smuffin return (SIGCONT); 2020Sstevel@tonic-gate case XSIGCLD: /* System V name for SIGCHLD */ 203*722Smuffin return (SIGCLD); 2040Sstevel@tonic-gate case XSIGTTIN: /* to readers pgrp upon background tty read */ 205*722Smuffin return (SIGTTIN); 2060Sstevel@tonic-gate case XSIGTTOU: /* like TTIN for output */ 207*722Smuffin return (SIGTTOU); 2080Sstevel@tonic-gate case XSIGIO: /* input/output possible signal */ 209*722Smuffin return (SIGIO); 2100Sstevel@tonic-gate case XSIGXCPU: /* exceeded CPU time limit */ 211*722Smuffin return (SIGXCPU); 2120Sstevel@tonic-gate case XSIGXFSZ: /* exceeded file size limit */ 213*722Smuffin return (SIGXFSZ); 2140Sstevel@tonic-gate case XSIGVTALRM: /* virtual time alarm */ 215*722Smuffin return (SIGVTALRM); 2160Sstevel@tonic-gate case XSIGPROF: /* profiling time alarm */ 217*722Smuffin return (SIGPROF); 2180Sstevel@tonic-gate case XSIGWINCH: /* window changed */ 219*722Smuffin return (SIGWINCH); 2200Sstevel@tonic-gate case XSIGUSR1: 221*722Smuffin return (SIGUSR1); 2220Sstevel@tonic-gate case XSIGUSR2: /* user defined signal 2 */ 223*722Smuffin return (SIGUSR2); 2240Sstevel@tonic-gate case XSIGPWR: /* user defined signal 2 */ 225*722Smuffin return (-1); 2260Sstevel@tonic-gate default: 227*722Smuffin return (sig); 2280Sstevel@tonic-gate } 2290Sstevel@tonic-gate } 2300Sstevel@tonic-gate 231*722Smuffin int 232*722Smuffin maptooldmask(int mask) 2330Sstevel@tonic-gate { 2340Sstevel@tonic-gate int omask; 2350Sstevel@tonic-gate 2360Sstevel@tonic-gate omask = mask & 0x7FFF; /* these signo are same */ 2370Sstevel@tonic-gate 2380Sstevel@tonic-gate if (mask & sigmask(XSIGURG)) 2390Sstevel@tonic-gate omask |= sigmask(SIGURG); 2400Sstevel@tonic-gate if (mask & sigmask(XSIGSTOP)) 2410Sstevel@tonic-gate omask |= sigmask(SIGSTOP); 2420Sstevel@tonic-gate if (mask & sigmask(XSIGTSTP)) 2430Sstevel@tonic-gate omask |= sigmask(SIGTSTP); 2440Sstevel@tonic-gate if (mask & sigmask(XSIGCONT)) 2450Sstevel@tonic-gate omask |= sigmask(SIGCONT); 2460Sstevel@tonic-gate if (mask & sigmask(XSIGCLD)) 2470Sstevel@tonic-gate omask |= sigmask(SIGCLD); 2480Sstevel@tonic-gate if (mask & sigmask(XSIGTTIN)) 2490Sstevel@tonic-gate omask |= sigmask(SIGTTIN); 2500Sstevel@tonic-gate if (mask & sigmask(XSIGTTOU)) 2510Sstevel@tonic-gate omask |= sigmask(SIGTTOU); 2520Sstevel@tonic-gate if (mask & sigmask(XSIGIO)) 2530Sstevel@tonic-gate omask |= sigmask(SIGIO); 2540Sstevel@tonic-gate if (mask & sigmask(XSIGXCPU)) 2550Sstevel@tonic-gate omask |= sigmask(SIGXCPU); 2560Sstevel@tonic-gate if (mask & sigmask(XSIGXFSZ)) 2570Sstevel@tonic-gate omask |= sigmask(SIGXFSZ); 2580Sstevel@tonic-gate if (mask & sigmask(XSIGVTALRM)) 2590Sstevel@tonic-gate omask |= sigmask(SIGVTALRM); 2600Sstevel@tonic-gate if (mask & sigmask(XSIGPROF)) 2610Sstevel@tonic-gate omask |= sigmask(SIGPROF); 2620Sstevel@tonic-gate if (mask & sigmask(XSIGWINCH)) 2630Sstevel@tonic-gate omask |= sigmask(SIGWINCH); 2640Sstevel@tonic-gate if (mask & sigmask(XSIGUSR1)) 2650Sstevel@tonic-gate omask |= sigmask(SIGUSR1); 2660Sstevel@tonic-gate if (mask & sigmask(XSIGUSR2)) 2670Sstevel@tonic-gate omask |= sigmask(SIGUSR2); 268*722Smuffin return (omask); 2690Sstevel@tonic-gate } 2700Sstevel@tonic-gate 2710Sstevel@tonic-gate 272*722Smuffin int 273*722Smuffin maptonewmask(int omask) 2740Sstevel@tonic-gate { 2750Sstevel@tonic-gate int mask; 2760Sstevel@tonic-gate 2770Sstevel@tonic-gate if (omask == -1) { 278*722Smuffin return (-1); 2790Sstevel@tonic-gate } 2800Sstevel@tonic-gate 2810Sstevel@tonic-gate mask = omask & 0x7FFF; /* these signo are the same */ 2820Sstevel@tonic-gate 2830Sstevel@tonic-gate if (omask & sigmask(SIGURG)) 2840Sstevel@tonic-gate mask |= sigmask(XSIGURG); 2850Sstevel@tonic-gate if (omask & sigmask(SIGSTOP)) 2860Sstevel@tonic-gate mask |= sigmask(XSIGSTOP); 2870Sstevel@tonic-gate if (omask & sigmask(SIGTSTP)) 2880Sstevel@tonic-gate mask |= sigmask(XSIGTSTP); 2890Sstevel@tonic-gate if (omask & sigmask(SIGCONT)) 2900Sstevel@tonic-gate mask |= sigmask(XSIGCONT); 2910Sstevel@tonic-gate if (omask & sigmask(SIGCLD)) 2920Sstevel@tonic-gate mask |= sigmask(XSIGCLD); 2930Sstevel@tonic-gate if (omask & sigmask(SIGTTIN)) 2940Sstevel@tonic-gate mask |= sigmask(XSIGTTIN); 2950Sstevel@tonic-gate if (omask & sigmask(SIGTTOU)) 2960Sstevel@tonic-gate mask |= sigmask(XSIGTTOU); 2970Sstevel@tonic-gate if (omask & sigmask(SIGIO)) 2980Sstevel@tonic-gate mask |= sigmask(XSIGIO); 2990Sstevel@tonic-gate if (omask & sigmask(SIGXCPU)) 3000Sstevel@tonic-gate mask |= sigmask(XSIGXCPU); 3010Sstevel@tonic-gate if (omask & sigmask(SIGXFSZ)) 3020Sstevel@tonic-gate mask |= sigmask(XSIGXFSZ); 3030Sstevel@tonic-gate if (omask & sigmask(SIGVTALRM)) 3040Sstevel@tonic-gate mask |= sigmask(XSIGVTALRM); 3050Sstevel@tonic-gate if (omask & sigmask(SIGPROF)) 3060Sstevel@tonic-gate mask |= sigmask(XSIGPROF); 3070Sstevel@tonic-gate if (omask & sigmask(SIGWINCH)) 3080Sstevel@tonic-gate mask |= sigmask(XSIGWINCH); 3090Sstevel@tonic-gate if (omask & sigmask(SIGUSR1)) 3100Sstevel@tonic-gate mask |= sigmask(XSIGUSR1); 3110Sstevel@tonic-gate if (omask & sigmask(SIGUSR2)) 3120Sstevel@tonic-gate mask |= sigmask(XSIGUSR2); 313*722Smuffin return (mask); 3140Sstevel@tonic-gate } 315