#ifdef WINDOWSNT
/* Cache for externally loaded libraries. */
Lisp_Object Vlibrary_cache;
+/* Original command line string as received from the OS. */
+static char *initial_cmdline;
+/* Original working directory when invoked. */
+static const char *initial_wd;
#endif
struct gflags gflags;
}
}
init_heap (use_dynamic_heap);
+ initial_cmdline = GetCommandLine ();
#endif
#if defined WINDOWSNT || defined HAVE_NTGUI
/* Set global variables used to detect Windows version. Do this as
#endif
emacs_wd = emacs_get_current_dir_name ();
+#ifdef WINDOWSNT
+ initial_wd = emacs_wd;
+#endif
#ifdef HAVE_PDUMPER
if (dumped_with_pdumper_p ())
pdumper_record_wd (emacs_wd);
(on some systems) with no argv. */
if (initial_argc < 1)
error ("No command line arguments known; unable to re-execute Emacs");
+#ifdef WINDOWSNT
+ if (w32_reexec_emacs (initial_cmdline, initial_wd) < 1)
+#else
if (execvp (*initial_argv, initial_argv) < 1)
+#endif
error ("Unable to re-execute Emacs");
}
return xstrdup (tgt);
}
+/* A replacement for Posix execvp, used to restart Emacs. This is
+ needed because the low-level Windows API to start processes accepts
+ the command-line arguments as a single string, so we cannot safely
+ use the MSVCRT execvp emulation, because elements of argv[] that
+ have embedded blanks and tabs will not be passed correctly to the
+ restarted Emacs. */
+int
+w32_reexec_emacs (char *cmd_line, const char *wdir)
+{
+ STARTUPINFO si;
+ SECURITY_ATTRIBUTES sec_attrs;
+ BOOL status;
+ PROCESS_INFORMATION proc_info;
+
+ GetStartupInfo (&si); /* Use the same startup info as the caller. */
+ sec_attrs.nLength = sizeof (sec_attrs);
+ sec_attrs.lpSecurityDescriptor = NULL;
+ sec_attrs.bInheritHandle = FALSE;
+
+ /* Make sure we are in the original directory, in case the command
+ line specifies the program as a relative file name. */
+ chdir (wdir);
+
+ status = CreateProcess (NULL, /* program */
+ cmd_line, /* command line */
+ &sec_attrs, /* process attributes */
+ NULL, /* thread attributes */
+ TRUE, /* inherit handles? */
+ NORMAL_PRIORITY_CLASS,
+ NULL, /* environment */
+ wdir, /* initial directory */
+ &si, /* startup info */
+ &proc_info);
+ if (status)
+ {
+ CloseHandle (proc_info.hThread);
+ CloseHandle (proc_info.hProcess);
+ exit (0);
+ }
+ errno = ENOEXEC;
+ return -1;
+}
+
/*
globals_of_w32 is used to initialize those global variables that
must always be initialized on startup even when the global variable
extern Lisp_Object w32_read_registry (HKEY, Lisp_Object, Lisp_Object);
+/* Used instead of execvp to restart Emacs. */
+extern int w32_reexec_emacs (char *, const char *);
+
#ifdef HAVE_GNUTLS
#include <gnutls/gnutls.h>