Select Git revision
lpc_signal.c
-
Fredrik Hübinette (Hubbe) authored
Rev: README:1.1 Rev: bin/create_testsuite:1.3 Rev: bin/hilfe.lpc:1.2 Rev: bin/rsif:1.2 Rev: bin/uhttpd.lpc:1.2 Rev: doc/simulated/open:1.1 Rev: lib/master.lpc:1.2 Rev: lib/simulate.lpc:1.4 Rev: lib/testsuite.lpc:1.3 Rev: src/BUGS:1.3 Rev: src/Makefile.in:1.6 Rev: src/Makefile.in.src:1.2 Rev: src/README:1.2 Rev: src/add_efun.c:1.2 Rev: src/add_efun.h:1.2 Rev: src/array.c:1.4 Rev: src/array.h:1.2 Rev: src/backend.c:1.3 Rev: src/backend.h:1.2 Rev: src/builtin_efuns.c:1.2 Rev: src/builtin_efuns.h:1.2 Rev: src/call_out.c:1.5 Rev: src/call_out.h:1.2 Rev: src/callback.c:1.2 Rev: src/callback.h:1.2 Rev: src/config.h:1.6 Rev: src/configure.in:1.9 Rev: src/debug.c:1.4 Rev: src/debug.h:1.4 Rev: src/docode.c:1.4 Rev: src/docode.h:1.2 Rev: src/dynamic_buffer.c:1.3 Rev: src/dynamic_buffer.h:1.2 Rev: src/efun.h:1.2 Rev: src/error.c:1.2 Rev: src/error.h:1.2 Rev: src/fd_control.c:1.2 Rev: src/fd_control.h:1.2 Rev: src/fsort.c:1.2 Rev: src/fsort.h:1.2 Rev: src/global.h:1.2 Rev: src/hashtable.c:1.2 Rev: src/hashtable.h:1.2 Rev: src/interpret.c:1.5 Rev: src/interpret.h:1.2 Rev: src/language.y:1.3 Rev: src/las.c:1.3 Rev: src/las.h:1.3 Rev: src/lex.c:1.3 Rev: src/lex.h:1.2 Rev: src/list.c:1.3 Rev: src/list.h:1.2 Rev: src/lpc_signal.c:1.1 Rev: src/lpc_signal.h:1.1 Rev: src/lpc_types.c:1.3 Rev: src/lpc_types.h:1.2 Rev: src/machine.h.in:1.3 Rev: src/macros.h:1.4 Rev: src/main.c:1.8 Rev: src/main.h:1.2 Rev: src/mapping.c:1.4 Rev: src/mapping.h:1.2 Rev: src/memory.c:1.3 Rev: src/memory.h:1.2 Rev: src/module.c:1.2 Rev: src/module.h:1.2 Rev: src/modules/files/Makefile.in:1.3 Rev: src/modules/files/Makefile.in.src:1.2 Rev: src/modules/files/configure.in:1.5 Rev: src/modules/files/datagram.c:1.2 Rev: src/modules/files/efuns.c:1.4 Rev: src/modules/files/file.c:1.5 Rev: src/modules/files/file.h:1.3 Rev: src/modules/files/file_machine.h.in:1.3 Rev: src/modules/files/socket.c:1.6 Rev: src/modules/math/Makefile.in:1.4 Rev: src/modules/math/Makefile.in.src:1.3 Rev: src/modules/math/math.c:1.2 Rev: src/modules/regexp/Makefile.in:1.3 Rev: src/modules/regexp/Makefile.in.src:1.2 Rev: src/modules/regexp/glue.c:1.2 Rev: src/modules/regexp/regexp.h:1.2 Rev: src/modules/sprintf/Makefile.in:1.3 Rev: src/modules/sprintf/Makefile.in.src:1.2 Rev: src/modules/sprintf/sprintf.c:1.2 Rev: src/object.c:1.3 Rev: src/object.h:1.2 Rev: src/opcodes.c:1.6 Rev: src/opcodes.h:1.2 Rev: src/operators.c:1.3 Rev: src/operators.h:1.2 Rev: src/otable.h:1.2 Rev: src/port.c:1.9 Rev: src/port.h:1.4 Rev: src/program.h:1.2 Rev: src/rusage.c:1.3 Rev: src/rusage.h:1.2 Rev: src/stralloc.c:1.3 Rev: src/stralloc.h:1.3 Rev: src/stuff.c:1.2 Rev: src/stuff.h:1.2 Rev: src/svalue.c:1.4 Rev: src/svalue.h:1.2 Rev: src/todo:1.2 Rev: src/types.h:1.6 Rev: src/ualarm.c:1.2
Fredrik Hübinette (Hubbe) authoredRev: README:1.1 Rev: bin/create_testsuite:1.3 Rev: bin/hilfe.lpc:1.2 Rev: bin/rsif:1.2 Rev: bin/uhttpd.lpc:1.2 Rev: doc/simulated/open:1.1 Rev: lib/master.lpc:1.2 Rev: lib/simulate.lpc:1.4 Rev: lib/testsuite.lpc:1.3 Rev: src/BUGS:1.3 Rev: src/Makefile.in:1.6 Rev: src/Makefile.in.src:1.2 Rev: src/README:1.2 Rev: src/add_efun.c:1.2 Rev: src/add_efun.h:1.2 Rev: src/array.c:1.4 Rev: src/array.h:1.2 Rev: src/backend.c:1.3 Rev: src/backend.h:1.2 Rev: src/builtin_efuns.c:1.2 Rev: src/builtin_efuns.h:1.2 Rev: src/call_out.c:1.5 Rev: src/call_out.h:1.2 Rev: src/callback.c:1.2 Rev: src/callback.h:1.2 Rev: src/config.h:1.6 Rev: src/configure.in:1.9 Rev: src/debug.c:1.4 Rev: src/debug.h:1.4 Rev: src/docode.c:1.4 Rev: src/docode.h:1.2 Rev: src/dynamic_buffer.c:1.3 Rev: src/dynamic_buffer.h:1.2 Rev: src/efun.h:1.2 Rev: src/error.c:1.2 Rev: src/error.h:1.2 Rev: src/fd_control.c:1.2 Rev: src/fd_control.h:1.2 Rev: src/fsort.c:1.2 Rev: src/fsort.h:1.2 Rev: src/global.h:1.2 Rev: src/hashtable.c:1.2 Rev: src/hashtable.h:1.2 Rev: src/interpret.c:1.5 Rev: src/interpret.h:1.2 Rev: src/language.y:1.3 Rev: src/las.c:1.3 Rev: src/las.h:1.3 Rev: src/lex.c:1.3 Rev: src/lex.h:1.2 Rev: src/list.c:1.3 Rev: src/list.h:1.2 Rev: src/lpc_signal.c:1.1 Rev: src/lpc_signal.h:1.1 Rev: src/lpc_types.c:1.3 Rev: src/lpc_types.h:1.2 Rev: src/machine.h.in:1.3 Rev: src/macros.h:1.4 Rev: src/main.c:1.8 Rev: src/main.h:1.2 Rev: src/mapping.c:1.4 Rev: src/mapping.h:1.2 Rev: src/memory.c:1.3 Rev: src/memory.h:1.2 Rev: src/module.c:1.2 Rev: src/module.h:1.2 Rev: src/modules/files/Makefile.in:1.3 Rev: src/modules/files/Makefile.in.src:1.2 Rev: src/modules/files/configure.in:1.5 Rev: src/modules/files/datagram.c:1.2 Rev: src/modules/files/efuns.c:1.4 Rev: src/modules/files/file.c:1.5 Rev: src/modules/files/file.h:1.3 Rev: src/modules/files/file_machine.h.in:1.3 Rev: src/modules/files/socket.c:1.6 Rev: src/modules/math/Makefile.in:1.4 Rev: src/modules/math/Makefile.in.src:1.3 Rev: src/modules/math/math.c:1.2 Rev: src/modules/regexp/Makefile.in:1.3 Rev: src/modules/regexp/Makefile.in.src:1.2 Rev: src/modules/regexp/glue.c:1.2 Rev: src/modules/regexp/regexp.h:1.2 Rev: src/modules/sprintf/Makefile.in:1.3 Rev: src/modules/sprintf/Makefile.in.src:1.2 Rev: src/modules/sprintf/sprintf.c:1.2 Rev: src/object.c:1.3 Rev: src/object.h:1.2 Rev: src/opcodes.c:1.6 Rev: src/opcodes.h:1.2 Rev: src/operators.c:1.3 Rev: src/operators.h:1.2 Rev: src/otable.h:1.2 Rev: src/port.c:1.9 Rev: src/port.h:1.4 Rev: src/program.h:1.2 Rev: src/rusage.c:1.3 Rev: src/rusage.h:1.2 Rev: src/stralloc.c:1.3 Rev: src/stralloc.h:1.3 Rev: src/stuff.c:1.2 Rev: src/stuff.h:1.2 Rev: src/svalue.c:1.4 Rev: src/svalue.h:1.2 Rev: src/todo:1.2 Rev: src/types.h:1.6 Rev: src/ualarm.c:1.2
lpc_signal.c 5.59 KiB
/*\
||| This file a part of uLPC, and is copyright by Fredrik Hubinette
||| uLPC is distributed as GPL (General Public License)
||| See the files COPYING and DISCLAIMER for more information.
\*/
#include "global.h"
#include "svalue.h"
#include "interpret.h"
#include "stralloc.h"
#include "add_efun.h"
#include "macros.h"
#include "backend.h"
#include "unistd.h"
#include <signal.h>
#ifdef NSIG
#define MAX_SIGNALS NSIG
#else
#define MAX_SIGNALS 256
#endif
#define SIGNAL_BUFFER 16384
static struct svalue signal_callbacks[MAX_SIGNALS];
static unsigned char sigbuf[SIGNAL_BUFFER];
static int firstsig, lastsig;
struct sigdesc
{
int signum;
char *signame;
};
/*
* All known signals
*/
static struct sigdesc signal_desc []={
#ifdef SIGHUP
{ SIGHUP, "SIGHUP" },
#endif
#ifdef SIGINT
{ SIGINT, "SIGINT" },
#endif
#ifdef SIGQUIT
{ SIGQUIT, "SIGQUIT" },
#endif
#ifdef SIGILL
{ SIGILL, "SIGILL" },
#endif
#ifdef SIGTRAP
{ SIGTRAP, "SIGTRAP" },
#endif
#ifdef SIGABRT
{ SIGABRT, "SIGABRT" },
#endif
#ifdef SIGIOT
{ SIGIOT, "SIGIOT" },
#endif
#ifdef SIGBUS
{ SIGBUS, "SIGBUS" },
#endif
#ifdef SIGFPE
{ SIGFPE, "SIGFPE" },
#endif
#ifdef SIGKILL
{ SIGKILL, "SIGKILL" },
#endif
#ifdef SIGUSR1
{ SIGUSR1, "SIGUSR1" },
#endif
#ifdef SIGSEGV
{ SIGSEGV, "SIGSEGV" },
#endif
#ifdef SIGUSR2
{ SIGUSR2, "SIGUSR2" },
#endif
#ifdef SIGPIPE
{ SIGPIPE, "SIGPIPE" },
#endif
#ifdef SIGALRM
{ SIGALRM, "SIGALRM" },
#endif
#ifdef SIGTERM
{ SIGTERM, "SIGTERM" },
#endif
#ifdef SIGSTKFLT
{ SIGSTKFLT, "SIGSTKFLT" },
#endif
#ifdef SIGCHLD
{ SIGCHLD, "SIGCHLD" },
#endif
#ifdef SIGCLD
{ SIGCLD, "SIGCLD" },
#endif
#ifdef SIGCONT
{ SIGCONT, "SIGCONT" },
#endif
#ifdef SIGSTOP
{ SIGSTOP, "SIGSTOP" },
#endif
#ifdef SIGTSTP
{ SIGTSTP, "SIGTSTP" },
#endif
#ifdef SIGTSTP
{ SIGTSTP, "SIGTSTP" },
#endif
#ifdef SIGTTIN
{ SIGTTIN, "SIGTTIN" },
#endif
#ifdef SIGTTIO
{ SIGTTIO, "SIGTTIO" },
#endif
#ifdef SIGURG
{ SIGURG, "SIGURG" },
#endif
#ifdef SIGXCPU
{ SIGXCPU, "SIGXCPU" },
#endif
#ifdef SIGXFSZ
{ SIGXFSZ, "SIGXFSZ" },
#endif
#ifdef SIGVTALRM
{ SIGVTALRM, "SIGVTALRM" },
#endif
#ifdef SIGPROF
{ SIGPROF, "SIGPROF" },
#endif
#ifdef SIGWINCH
{ SIGWINCH, "SIGWINCH" },
#endif
#ifdef SIGIO
{ SIGIO, "SIGIO" },
#endif
#ifdef SIGPOLL
{ SIGPOLL, "SIGPOLL" },
#endif
#ifdef SIGLOST
{ SIGLOST, "SIGLOST" },
#endif
#ifdef SIGPWR
{ SIGPWR, "SIGPWR" },
#endif
#ifdef SIGUNUSED
{ SIGUNUSED, "SIGUNUSED" },
#endif
{ -1, "END" } /* Notused */
};
static RETSIGTYPE receive_signal(int signum)
{
int tmp;
tmp=firstsig+1;
if(tmp == SIGNAL_BUFFER) tmp=0;
if(tmp != lastsig)
sigbuf[firstsig=tmp]=signum;
signal(signum, receive_signal);
}
void check_signals()
{
extern int d_flag;
#ifdef DEBUG
if(d_flag>5) do_debug(0);
#endif
if(firstsig != lastsig)
{
int tmp=firstsig;
while(lastsig != tmp)
{
if(++lastsig == SIGNAL_BUFFER) lastsig=0;
push_int(sigbuf[lastsig]);
apply_svalue(signal_callbacks + sigbuf[lastsig], 1);
pop_stack();
}
}
}
/* Get the name of a signal given the number */
static char *signame(int sig)
{
int e;
for(e=0;e<NELEM(signal_desc)-1;e++)
{
if(sig==signal_desc[e].signum)
return signal_desc[e].signame;
}
return 0;
}
/* Get the signal's number given the name */
static int signum(char *name)
{
int e;
for(e=0;e<NELEM(signal_desc)-1;e++)
{
if(!strcasecmp(name,signal_desc[e].signame) ||
!strcasecmp(name,signal_desc[e].signame+3) )
return signal_desc[e].signum;
}
return -1;
}
static void f_signal(int args)
{
int signum;
if(args < 1)
error("Too few arguments to signal()\n");
if(args == 1)
{
push_int(0);
args++;
}
if(sp[-args].type != T_INT)
{
error("Bad argument 1 to signal()\n");
}
signum=sp[-args].u.integer;
if(signum <0 || signum >=MAX_SIGNALS)
{
error("Signal out of range.\n");
}
assign_svalue(signal_callbacks + signum, sp+1-args);
if(IS_ZERO(sp+1-args))
{
/* Not good enough, we need the uLPC default */
signal(signum,SIG_DFL);
}else{
signal(signum,receive_signal);
}
pop_n_elems(args);
}
static void f_signum(int args)
{
int i;
if(args < 1)
error("Too few arguments to signum()\n");
if(sp[-args].type != T_STRING)
error("Bad argument 1 to signum()\n");
i=signum(sp[-args].u.string->str);
pop_n_elems(args);
push_int(i);
}
static void f_signame(int args)
{
char *n;
if(args < 1)
error("Too few arguments to signame()\n");
if(sp[-args].type != T_INT)
error("Bad argument 1 to signame()\n");
n=signame(sp[-args].u.integer);
pop_n_elems(args);
if(n)
push_string(make_shared_string(n));
else
push_int(0);
}
static void f_kill(INT32 args)
{
if(args < 2)
error("Too few arguments to kill().\n");
if(sp[-args].type != T_INT)
error("Bad argument 1 to kill().\n");
if(sp[1-args].type != T_INT)
error("Bad argument 1 to kill().\n");
sp[-args].u.integer=!kill(sp[-args].u.integer,sp[1-args].u.integer);
pop_n_elems(args-1);
}
static void f_getpid(INT32 args)
{
pop_n_elems(args);
push_int(getpid());
}
void init_signals()
{
int e;
for(e=0;e<MAX_SIGNALS;e++)
signal_callbacks[e].type=T_INT;
firstsig=lastsig=sigbuf[0];
add_efun("signal",f_signal,"function(int,mixed|void:void)",OPT_SIDE_EFFECT);
add_efun("kill",f_kill,"function(int,int:int)",OPT_SIDE_EFFECT);
add_efun("signame",f_signame,"function(int:string)",0);
add_efun("signum",f_signum,"function(string:int)",0);
add_efun("getpid",f_getpid,"function(:int)",0);
}
void exit_signals()
{
int e;
for(e=0;e<MAX_SIGNALS;e++)
{
free_svalue(signal_callbacks+e);
signal_callbacks[e].type=T_INT;
}
}