fixed signal handling, factoroids

cvs
Slava Pestov 2004-11-09 17:29:25 +00:00
parent 9f938842e3
commit a3bb6acf52
7 changed files with 59 additions and 76 deletions

View File

@ -31,8 +31,10 @@ Makefile - Makefile for building C interpreter.
native/ - source code for Factor interpreter written in C. native/ - source code for Factor interpreter written in C.
library/platform/native - C interpreter-specific code library/platform/native - C interpreter-specific code
f - compiled C interpreter - needs image to run f - compiled C interpreter - needs image to run
boot.image.le - image for x86 boot.image.le32 - image for x86
boot.image.be - image for 32-bit SPARC and 32-bit PowerPC boot.image.le64 - image for AMD64
boot.image.be32 - image for 32-bit SPARC and 32-bit PowerPC
boot.image.be64 - iamge for 64-bit SPARC and 64-bit PowerPC
Notes on the C interpreter Notes on the C interpreter
-------------------------- --------------------------
@ -40,20 +42,3 @@ Notes on the C interpreter
When you run the interpreter with a boot image, it loads a When you run the interpreter with a boot image, it loads a
bunch of files and saves a 'factor.image'. Run the bunch of files and saves a 'factor.image'. Run the
interpreter again with this image. interpreter again with this image.
At the moment it assumes a 32-bit architecture. Your C
compiler's types must be as follows:
short - signed 16 bits
long - signed 32 bits
long long - signed 64 bits
double -IEEE double precision 64-bit float
Moving to 64-bits would require a few changes in the image
cross-compiler, namely in the way it packs strings.
Not everything has been implemented yet. However, a lot
already works. Compare the output of this in the C and
Java interpreters to see how they differ:
"vocabularies" get describe

View File

@ -1,5 +1,12 @@
! Currently the plugin doesn't handle GENERIC: and M:, so we ! A simple space shooter.
! disable the parser. too many errors :sidekick.parser=none: !
! To play the game:
!
! ./f factor.image -libraries:sdl=libSDL.so -libraries:sdl-gfx=libSDL_gfx.so
!
! "examples/oop.factor" run-file
! "examples/factoroids.factor" run-file
IN: factoroids IN: factoroids
USE: combinators USE: combinators
@ -267,3 +274,6 @@ SYMBOL: event
] with-screen ; ] with-screen ;
factoroids factoroids
! Currently the plugin doesn't handle GENERIC: and M:, so we
! disable the parser. too many errors :sidekick.parser=none:

View File

@ -94,18 +94,6 @@ USE: words
: ffi-error ( obj -- ) : ffi-error ( obj -- )
"FFI: " write print ; "FFI: " write print ;
: datastack-underflow-error ( obj -- )
drop "Datastack underflow" print ;
: datastack-overflow-error ( obj -- )
drop "Datastack overflow" print ;
: callstack-underflow-error ( obj -- )
drop "Callstack underflow" print ;
: callstack-overflow-error ( obj -- )
drop "Callstack overflow" print ;
: port-closed-error ( obj -- ) : port-closed-error ( obj -- )
"Port closed: " write . ; "Port closed: " write . ;
@ -126,10 +114,6 @@ USE: words
c-string-error c-string-error
ffi-disabled-error ffi-disabled-error
ffi-error ffi-error
datastack-underflow-error
datastack-overflow-error
callstack-underflow-error
callstack-overflow-error
port-closed-error port-closed-error
} vector-nth execute ; } vector-nth execute ;

View File

@ -18,9 +18,12 @@ void critical_error(char* msg, CELL tagged)
exit(1); exit(1);
} }
void throw_error(CELL error) void throw_error(CELL error, bool keep_stacks)
{ {
thrown_error = error; thrown_error = error;
thrown_keep_stacks = keep_stacks;
thrown_ds = ds;
thrown_cs = cs;
/* Return to run() method */ /* Return to run() method */
siglongjmp(toplevel,1); siglongjmp(toplevel,1);
@ -28,30 +31,32 @@ void throw_error(CELL error)
void primitive_throw(void) void primitive_throw(void)
{ {
throw_error(dpop()); throw_error(dpop(),true);
}
void early_error(CELL error)
{
if(userenv[BREAK_ENV] == F)
{
/* Crash at startup */
fprintf(stderr,"Error %ld thrown before BREAK_ENV set\n",to_fixnum(error));
fflush(stderr);
exit(1);
}
} }
void general_error(CELL error, CELL tagged) void general_error(CELL error, CELL tagged)
{ {
CELL c = cons(error,cons(tagged,F)); early_error(error);
if(userenv[BREAK_ENV] == F) throw_error(cons(error,cons(tagged,F)),true);
{ }
/* Crash at startup */
fprintf(stderr,"Error thrown before BREAK_ENV set\n");
fprintf(stderr,"Error #%ld\n",to_fixnum(error));
if(error == ERROR_TYPE)
{
CELL obj = untag_cons(untag_cons(tagged)->cdr)->car;
fprintf(stderr,"Type #%ld\n",to_fixnum( /* It is not safe to access 'ds' from a signal handler, so we just not
untag_cons(tagged)->car)); touch it */
fprintf(stderr,"Object %ld\n",obj); void signal_error(int signal)
fprintf(stderr,"Got type #%ld\n",type_of(obj)); {
} early_error(ERROR_SIGNAL);
fflush(stderr); throw_error(cons(ERROR_SIGNAL,cons(tag_fixnum(signal),F)),false);
exit(1);
}
throw_error(c);
} }
void type_error(CELL type, CELL tagged) void type_error(CELL type, CELL tagged)

View File

@ -13,21 +13,22 @@
#define ERROR_C_STRING (12<<3) #define ERROR_C_STRING (12<<3)
#define ERROR_FFI_DISABLED (13<<3) #define ERROR_FFI_DISABLED (13<<3)
#define ERROR_FFI (14<<3) #define ERROR_FFI (14<<3)
#define ERROR_DATASTACK_UNDERFLOW (15<<3) #define ERROR_CLOSED (15<<3)
#define ERROR_DATASTACK_OVERFLOW (16<<3)
#define ERROR_CALLSTACK_UNDERFLOW (17<<3)
#define ERROR_CALLSTACK_OVERFLOW (18<<3)
#define ERROR_CLOSED (19<<3)
/* When throw_error throws an error, it sets this global and /* When throw_error throws an error, it sets this global and
longjmps back to the top-level. */ longjmps back to the top-level. */
CELL thrown_error; CELL thrown_error;
CELL thrown_keep_stacks;
CELL thrown_ds;
CELL thrown_cs;
void init_errors(void); void init_errors(void);
void fatal_error(char* msg, CELL tagged); void fatal_error(char* msg, CELL tagged);
void critical_error(char* msg, CELL tagged); void critical_error(char* msg, CELL tagged);
void throw_error(CELL object); void throw_error(CELL error, bool keep_stacks);
void early_error(CELL error);
void general_error(CELL error, CELL tagged); void general_error(CELL error, CELL tagged);
void signal_error(int signal);
void type_error(CELL type, CELL tagged); void type_error(CELL type, CELL tagged);
void primitive_throw(void); void primitive_throw(void);
void range_error(CELL tagged, FIXNUM index, CELL max); void range_error(CELL tagged, FIXNUM index, CELL max);

View File

@ -18,7 +18,14 @@ void run(void)
sigsetjmp(toplevel, 1); sigsetjmp(toplevel, 1);
if(thrown_error != F) if(thrown_error != F)
{ {
if(thrown_keep_stacks)
{
ds = thrown_ds;
cs = thrown_cs;
}
else
fix_stacks(); fix_stacks();
dpush(thrown_error); dpush(thrown_error);
/* Notify any 'catch' blocks */ /* Notify any 'catch' blocks */
call(userenv[BREAK_ENV]); call(userenv[BREAK_ENV]);

View File

@ -2,12 +2,6 @@
void signal_handler(int signal, siginfo_t* siginfo, void* uap) void signal_handler(int signal, siginfo_t* siginfo, void* uap)
{ {
general_error(ERROR_SIGNAL,tag_fixnum(signal));
}
void memory_signal_handler(int signal, siginfo_t* siginfo, void* uap)
{
fprintf(stderr,"memory signal\n");
if(active.here > active.limit) if(active.here > active.limit)
{ {
fprintf(stderr,"Out of memory\n"); fprintf(stderr,"Out of memory\n");
@ -18,7 +12,7 @@ void memory_signal_handler(int signal, siginfo_t* siginfo, void* uap)
exit(1); exit(1);
} }
else else
general_error(ERROR_SIGNAL,tag_fixnum(signal)); signal_error(signal);
} }
/* Called from a signal handler. XXX - is this safe? */ /* Called from a signal handler. XXX - is this safe? */
@ -41,19 +35,16 @@ void init_signals(void)
{ {
struct sigaction custom_sigaction; struct sigaction custom_sigaction;
struct sigaction profiling_sigaction; struct sigaction profiling_sigaction;
struct sigaction memory_sigaction;
struct sigaction ign_sigaction; struct sigaction ign_sigaction;
custom_sigaction.sa_sigaction = signal_handler; custom_sigaction.sa_sigaction = signal_handler;
custom_sigaction.sa_flags = SA_SIGINFO; custom_sigaction.sa_flags = SA_SIGINFO;
profiling_sigaction.sa_sigaction = call_profiling_step; profiling_sigaction.sa_sigaction = call_profiling_step;
profiling_sigaction.sa_flags = SA_SIGINFO; profiling_sigaction.sa_flags = SA_SIGINFO;
memory_sigaction.sa_sigaction = memory_signal_handler;
memory_sigaction.sa_flags = SA_SIGINFO;
ign_sigaction.sa_handler = SIG_IGN; ign_sigaction.sa_handler = SIG_IGN;
sigaction(SIGABRT,&custom_sigaction,NULL); sigaction(SIGABRT,&custom_sigaction,NULL);
sigaction(SIGFPE,&custom_sigaction,NULL); sigaction(SIGFPE,&custom_sigaction,NULL);
sigaction(SIGBUS,&memory_sigaction,NULL); sigaction(SIGBUS,&custom_sigaction,NULL);
sigaction(SIGSEGV,&memory_sigaction,NULL); sigaction(SIGSEGV,&custom_sigaction,NULL);
sigaction(SIGPIPE,&ign_sigaction,NULL); sigaction(SIGPIPE,&ign_sigaction,NULL);
sigaction(SIGPROF,&profiling_sigaction,NULL); sigaction(SIGPROF,&profiling_sigaction,NULL);
} }