
#include "include.h"

#include <signal.h>
#include "usig.h"

char signals_handled[];

gcl_signal(signo,handler)
     int signo;
     void (*handler)();
{ char *p = signals_handled;

  while (*p)
    { if (*p==signo)
	{our_signal_handler[signo] = handler;
	 handler = main_signal_handler;
	 break;
       }
      p++;}

  {      
  
#ifdef HAVE_SIGACTION
    struct sigaction action;
    action.sa_handler = handler;
    action.sa_flags = SA_RESTART | (signo == SIGSEGV || signo == SIGBUS ? SV_ONSTACK : 0)
#ifdef SA_SIGINFO
    | SA_SIGINFO
#endif      
      ;
    sigemptyset(&action.sa_mask);
    sigaddset(&action.sa_mask,signo);
    sigaction(signo,&action,0);
#else
#ifdef HAVE_SIGVEC
    struct sigvec vec;
    vec.sv_handler =  handler;
    vec.sv_flags =  (signo == SIGSEGV || signo == SIGBUS ? SV_ONSTACK : 0);
    vec.sv_mask = sigmask(signo);
    sigvec(signo,&vec,0);
#else
    signal(signo,handler);
#endif
#endif
  }
}


void segmentation_catcher();

/* catch certain signals */
void install_segmentation_catcher()
{
#ifdef INSTALL_SEGMENTATION_CATCHER
  INSTALL_SEGMENTATION_CATCHER;
#else
#ifdef SIGSEGV
       (void) gcl_signal(SIGSEGV,segmentation_catcher);
#endif
#endif
}

int catch_fatal=1;

error(s)
{
        if (catch_fatal>0 && interrupt_enable )
	  {catch_fatal = -1;
	   FEerror("Caught fatal error [memory may be damaged]"); }
	
	fprintf(stderr,"\nFatal error: %s.\n", s);
	fflush(stderr);

	abort();

}


void
sigfpe()
{
	gcl_signal(SIGFPE, sigfpe);
	FEerror("Floating-point exception.", 0);
}


void
sigint()
{
 terminal_interrupt(1);
 gcl_signal(SIGINT, sigint);
}


void
sigalrm()
{
  terminal_interrupt(1);
}

void
install_default_signals()
{	gcl_signal(SIGFPE, sigfpe);
	gcl_signal(SIGINT, sigint);
	install_segmentation_catcher();
      }


	

