/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License, Version 1.0 only
* (the "License"). You may not use this file except in compliance
* with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */
/* All Rights Reserved */
/*
* University Copyright- Copyright (c) 1982, 1986, 1988
* The Regents of the University of California
* All Rights Reserved
*
* University Acknowledgment- Portions of this document are derived from
* software developed by the University of California, Berkeley, and its
* contributors.
*/
#pragma ident "%Z%%M% %I% %E% SMI"
/*
* mailx -- a modified version of a University of California at Berkeley
* mail program
*/
/*
* This code is only compiled in if SIG_HOLD is not defined!
*
* Retrofit new signal interface to old signal primitives.
* Supported routines:
* sigsys(sig, func)
* sigset(sig, func)
* sighold(sig)
* sigrelse(sig)
* sigignore(sig)
* sigpause(sig)
* Also,
* sigchild()
* to set all held signals to ignored signals in the
* child process after fork(2)
*/
#include <signal.h>
#ifndef SIG_HOLD
# include <errno.h>
# include <setjmp.h>
# include <stdio.h>
extern int errno;
typedef void (*sigtype)();
#ifndef SIG_ERR
#endif
void _Sigtramp();
/*
* The following helps us keep the extended signal semantics together.
* We remember for each signal the address of the function we're
* supposed to call. s_func is SIG_DFL / SIG_IGN if appropriate.
*/
static struct sigtable {
/*
* Signal flag values.
*/
/*
* Approximate sigsys() system call
* This is almost useless since one only calls sigsys()
* in the child of a vfork(). If you have vfork(), you have new signals
* anyway. The real sigsys() does all the stuff needed to support
* the real sigset() library. We don't bother here, assuming that
* you are either ignoring or defaulting a signal in the child.
*/
{
return(old);
}
/*
* Set the (permanent) disposition of a signal.
* If the signal is subsequently (or even now) held,
* the action you set here can be enabled using sigrelse().
*/
{
return(SIG_ERR);
}
/*
* Does anyone actually call sigset with SIG_HOLD!?
*/
return(old);
}
/*
* If signal has been held, must retain
* the catch so that we can note occurrance
* of signal.
*/
else
return(old);
}
/*
* Clear pending signal
*/
return(old);
}
return(old);
}
/*
* Hold a signal.
* This CAN be tricky if the signal's disposition is SIG_DFL.
* In that case, we still catch the signal so we can note it
*/
{
return(SIG_ERR);
}
return(old);
/*
* When the default action is required, we have to
* set up to catch the signal to note signal's occurrance.
*/
}
return(old);
}
/*
* Release a signal
* If the signal occurred while we had it held, cause the signal.
*/
{
return(SIG_ERR);
}
return(old);
/*
* If disposition was the default, then we can unset the
* catch to _Sigtramp() and let the system do the work.
*/
return(old);
}
/*
* Ignore a signal.
*/
{
}
/*
* Pause, waiting for sig to occur.
* We assume LUSER called us with the signal held.
* When we got the signal, mark the signal as having
* occurred. It will actually cause something when
* the signal is released.
*/
int
{
return;
}
pause();
}
/*
* In the child process after fork(2), set the disposition of all held
* signals to SIG_IGN. This is a new procedure not in the real sigset()
* package, provided for retrofitting purposes.
*/
int
sigchild(void)
{
register int i;
for (i = 1; i <= NSIG; i++)
}
/*
* Return the current disposition of a signal
* If we have not set this signal before, we have to
* ask the system
*/
{
return(SIG_ERR);
}
/*
* If we have no knowledge of this signal,
* ask the system, then save the result for later.
*/
return(old);
}
/*
* If we have set this signal before, then sigset()
* will have been careful to leave something meaningful
* in s_func.
*/
}
/*
* The following routine gets called for any signal
* that is to be trapped to a user function.
*/
void
{
return;
}
top:
/*
* If signal being paused on, wakeup sigpause()
*/
/*
* If signal is being held, mark its table entry
* so we can trigger it when signal is released.
* Then just return.
*/
return;
}
/*
* If the signal is being ignored, just return.
* This would make SIGCONT more normal, but of course
* any system with SIGCONT also has the new signal pkg, so...
*/
return;
/*
* If the signal is SIG_DFL, then we probably got here
* by holding the signal, having it happen, then releasing
* the signal.
*/
/* Will we get back here? */
return;
}
/*
* Looks like we should just cause the signal...
* We hold the signal for the duration of the user's
* code with the signal re-enabled. If the signal
* happens again while in user code, we will recursively
* trap here and mark that we had another occurance
* and return to the user's trap code. When we return
* from there, we can cause the signal again.
*/
/*
* If the signal re-occurred while in the user's routine,
* just go try it again...
*/
goto top;
}
#endif