#include <sys/file.h>
#include <unistd.h>
-#include "lisp.h"
+#include <ignore-value.h>
-#ifdef HAVE_WINDOW_SYSTEM
-#include TERM_HEADER
-#endif /* HAVE_WINDOW_SYSTEM */
+#include "lisp.h"
#ifdef WINDOWSNT
#include <fcntl.h>
#include "cygw32.h"
#endif
+#ifdef HAVE_WINDOW_SYSTEM
+#include TERM_HEADER
+#endif /* HAVE_WINDOW_SYSTEM */
+
#ifdef NS_IMPL_GNUSTEP
/* At least under Debian, GSConfig is in a subdirectory. --Stef */
#include <GNUstepBase/GSConfig.h>
#include "window.h"
#include "systty.h"
+#include "atimer.h"
#include "blockinput.h"
#include "syssignal.h"
#include "process.h"
/* Empty lisp strings. To avoid having to build any others. */
Lisp_Object empty_unibyte_string, empty_multibyte_string;
+#ifdef WINDOWSNT
+/* Cache for externally loaded libraries. */
+Lisp_Object Vlibrary_cache;
+#endif
+
/* Set after Emacs has started up the first time.
Prevents reinitialization of the Lisp world and keymaps
on subsequent starts. */
section of the Emacs manual or the file BUGS.\n"
\f
-/* Signal code for the fatal signal that was received. */
-static int fatal_error_code;
-
/* True if handling a fatal error already. */
bool fatal_error_in_progress;
-/* Handle bus errors, invalid instruction, etc. */
-static void
-handle_fatal_signal (int sig)
-{
- fatal_error_backtrace (sig, 10);
-}
-
-static void
-deliver_fatal_signal (int sig)
-{
- handle_on_main_thread (sig, handle_fatal_signal);
-}
-
/* Report a fatal error due to signal SIG, output a backtrace of at
most BACKTRACE_LIMIT lines, and exit. */
_Noreturn void
-fatal_error_backtrace (int sig, int backtrace_limit)
+terminate_due_to_signal (int sig, int backtrace_limit)
{
- fatal_error_code = sig;
signal (sig, SIG_DFL);
-
- TOTALLY_UNBLOCK_INPUT;
+ totally_unblock_input ();
/* If fatal error occurs in code below, avoid infinite recursion. */
if (! fatal_error_in_progress)
}
/* Signal the same code; this time it will really be fatal.
- Remember that since we're in a signal handler, the signal we're
- going to send is probably blocked, so we have to unblock it if we
- want to really receive it. */
+ Since we're in a signal handler, the signal is blocked, so we
+ have to unblock it if we want to really receive it. */
#ifndef MSDOS
{
sigset_t unblocked;
sigemptyset (&unblocked);
- sigaddset (&unblocked, fatal_error_code);
+ sigaddset (&unblocked, sig);
pthread_sigmask (SIG_UNBLOCK, &unblocked, 0);
}
#endif
- kill (getpid (), fatal_error_code);
+ emacs_raise (sig);
/* This shouldn't be executed, but it prevents a warning. */
exit (1);
#ifdef SIGDANGER
/* Handler for SIGDANGER. */
-static void deliver_danger_signal (int);
-
static void
handle_danger_signal (int sig)
{
- struct sigaction action;
- emacs_sigaction_init (&action, deliver_danger_signal);
- sigaction (sig, &action, 0);
-
malloc_warning ("Operating system warns that virtual memory is running low.\n");
/* It might be unsafe to call do_auto_save now. */
static void
deliver_danger_signal (int sig)
{
- handle_on_main_thread (sig, handle_danger_signal);
+ deliver_process_signal (sig, handle_danger_signal);
}
#endif
\f
#endif
char stack_bottom_variable;
bool do_initial_setlocale;
+ bool dumping;
int skip_args = 0;
#ifdef HAVE_SETRLIMIT
struct rlimit rlim;
char dname_arg2[80];
#endif /* DAEMON_MUST_EXEC */
char *ch_to_dir;
- struct sigaction fatal_error_action;
#if GC_MARK_STACK
stack_base = &dummy;
exit (1);
}
+ dumping = !initialized && (strcmp (argv[argc - 1], "dump") == 0
+ || strcmp (argv[argc - 1], "bootstrap") == 0);
#ifdef HAVE_PERSONALITY_LINUX32
- if (!initialized
- && (strcmp (argv[argc-1], "dump") == 0
- || strcmp (argv[argc-1], "bootstrap") == 0)
- && ! getenv ("EMACS_HEAP_EXEC"))
+ if (dumping && ! getenv ("EMACS_HEAP_EXEC"))
{
static char heapexec[] = "EMACS_HEAP_EXEC=true";
/* Set this so we only do this once. */
#endif
}
- init_signals ();
- emacs_sigaction_init (&fatal_error_action, deliver_fatal_signal);
-
- /* Don't catch SIGHUP if dumping. */
- if (1
-#ifndef CANNOT_DUMP
- && initialized
-#endif
- )
- {
- /* In --batch mode, don't catch SIGHUP if already ignored.
- That makes nohup work. */
- bool catch_SIGHUP = !noninteractive;
- if (!catch_SIGHUP)
- {
- struct sigaction old_action;
- sigaction (SIGHUP, 0, &old_action);
- catch_SIGHUP = old_action.sa_handler != SIG_IGN;
- }
- if (catch_SIGHUP)
- sigaction (SIGHUP, &fatal_error_action, 0);
- }
-
- if (
-#ifndef CANNOT_DUMP
- ! noninteractive || initialized
-#else
- 1
-#endif
- )
- {
- /* Don't catch these signals in batch mode if dumping.
- On some machines, this sets static data that would make
- signal fail to work right when the dumped Emacs is run. */
- sigaction (SIGQUIT, &fatal_error_action, 0);
- sigaction (SIGILL, &fatal_error_action, 0);
- sigaction (SIGTRAP, &fatal_error_action, 0);
-#ifdef SIGUSR1
- add_user_signal (SIGUSR1, "sigusr1");
-#endif
-#ifdef SIGUSR2
- add_user_signal (SIGUSR2, "sigusr2");
-#endif
-#ifdef SIGABRT
- sigaction (SIGABRT, &fatal_error_action, 0);
-#endif
-#ifdef SIGHWE
- sigaction (SIGHWE, &fatal_error_action, 0);
-#endif
-#ifdef SIGPRE
- sigaction (SIGPRE, &fatal_error_action, 0);
-#endif
-#ifdef SIGORE
- sigaction (SIGORE, &fatal_error_action, 0);
-#endif
-#ifdef SIGUME
- sigaction (SIGUME, &fatal_error_action, 0);
-#endif
-#ifdef SIGDLK
- sigaction (SIGDLK, &fatal_error_action, 0);
-#endif
-#ifdef SIGCPULIM
- sigaction (SIGCPULIM, &fatal_error_action, 0);
-#endif
-#ifdef SIGIOT
- /* This is missing on some systems - OS/2, for example. */
- sigaction (SIGIOT, &fatal_error_action, 0);
-#endif
-#ifdef SIGEMT
- sigaction (SIGEMT, &fatal_error_action, 0);
-#endif
- sigaction (SIGFPE, &fatal_error_action, 0);
-#ifdef SIGBUS
- sigaction (SIGBUS, &fatal_error_action, 0);
-#endif
- sigaction (SIGSEGV, &fatal_error_action, 0);
-#ifdef SIGSYS
- sigaction (SIGSYS, &fatal_error_action, 0);
-#endif
- /* May need special treatment on MS-Windows. See
- http://lists.gnu.org/archive/html/emacs-devel/2010-09/msg01062.html
- Please update the doc of kill-emacs, kill-emacs-hook, and
- NEWS if you change this.
- */
- if (noninteractive)
- sigaction (SIGINT, &fatal_error_action, 0);
- sigaction (SIGTERM, &fatal_error_action, 0);
-#ifdef SIGXCPU
- sigaction (SIGXCPU, &fatal_error_action, 0);
-#endif
-#ifdef SIGXFSZ
- sigaction (SIGXFSZ, &fatal_error_action, 0);
-#endif /* SIGXFSZ */
-
-#ifdef SIGDANGER
- /* This just means available memory is getting low. */
- {
- struct sigaction action;
- emacs_sigaction_init (&action, deliver_danger_signal);
- sigaction (SIGDANGER, &action, 0);
- }
-#endif
-
-#ifdef AIX
-/* 20 is SIGCHLD, 21 is SIGTTIN, 22 is SIGTTOU. */
- sigaction (SIGXCPU, &fatal_error_action, 0);
- sigaction (SIGIOINT, &fatal_error_action, 0);
- sigaction (SIGGRANT, &fatal_error_action, 0);
- sigaction (SIGRETRACT, &fatal_error_action, 0);
- sigaction (SIGSOUND, &fatal_error_action, 0);
- sigaction (SIGMSG, &fatal_error_action, 0);
-#endif /* AIX */
- }
+ init_signals (dumping);
noninteractive1 = noninteractive;
}
init_eval ();
- init_data ();
init_atimer ();
running_asynch_code = 0;
init_random ();
globals_of_w32 ();
/* Initialize environment from registry settings. */
init_environment (argv);
- init_ntproc (); /* must precede init_editfns. */
+ init_ntproc (dumping); /* must precede init_editfns. */
#endif
/* Initialize and GC-protect Vinitial_environment and
/* egetenv is a pretty low-level facility, which may get called in
many circumstances; it seems flimsy to put off initializing it
until calling init_callproc. Do not do it when dumping. */
- if (initialized || ((strcmp (argv[argc-1], "dump") != 0
- && strcmp (argv[argc-1], "bootstrap") != 0)))
+ if (! dumping)
set_initial_environment ();
/* AIX crashes are reported in system versions 3.2.3 and 3.2.4
syms_of_ntterm ();
#endif /* WINDOWSNT */
+ syms_of_profiler ();
+
keys_of_casefiddle ();
keys_of_cmds ();
keys_of_buffer ();
{
reset_all_sys_modes ();
if (sig && sig != SIGTERM)
- fprintf (stderr, "Fatal error %d: %s", sig, strsignal (sig));
+ {
+ static char const format[] = "Fatal error %d: ";
+ char buf[sizeof format - 2 + INT_STRLEN_BOUND (int)];
+ int buflen = sprintf (buf, format, sig);
+ char const *sig_desc = safe_strsignal (sig);
+ ignore_value (write (STDERR_FILENO, buf, buflen));
+ ignore_value (write (STDERR_FILENO, sig_desc, strlen (sig_desc)));
+ }
}
}
#else
unrequest_sigio ();
ignore_sigio ();
-#ifdef WINDOWSNT
- term_ntproc ();
-#endif
-
/* Do this only if terminating normally, we want glyph matrices
etc. in a core dump. */
if (sig == 0 || sig == SIGTERM)
#ifdef HAVE_LIBXML2
xml_cleanup_parser ();
#endif
+
+#ifdef WINDOWSNT
+ term_ntproc (0);
+#endif
}
free (malloc_state_ptr);
#endif
+#ifdef WINDOWSNT
+ Vlibrary_cache = Qnil;
+#endif
+#ifdef HAVE_WINDOW_SYSTEM
+ reset_image_types ();
+#endif
+
Vpurify_flag = tem;
return unbind_to (count, Qnil);
Vdynamic_library_alist = Qnil;
Fput (intern_c_string ("dynamic-library-alist"), Qrisky_local_variable, Qt);
+#ifdef WINDOWSNT
+ Vlibrary_cache = Qnil;
+ staticpro (&Vlibrary_cache);
+#endif
+
/* Make sure IS_DAEMON starts up as false. */
daemon_pipe[1] = 0;
}