]> code.delx.au - gnu-emacs/blob - src/emacs.c
*** empty log message ***
[gnu-emacs] / src / emacs.c
1 /* Fully extensible Emacs, running on Unix, intended for GNU.
2 Copyright (C) 1985,86,87,93,94,95,97,98,1999,2001
3 Free Software Foundation, Inc.
4
5 This file is part of GNU Emacs.
6
7 GNU Emacs is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
11
12 GNU Emacs is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GNU Emacs; see the file COPYING. If not, write to
19 the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA. */
21
22
23 #include <config.h>
24 #include <signal.h>
25 #include <errno.h>
26 #include <stdio.h>
27
28 #include <sys/types.h>
29 #include <sys/file.h>
30
31 #ifdef VMS
32 #include <ssdef.h>
33 #endif
34
35 #ifdef HAVE_UNISTD_H
36 #include <unistd.h>
37 #endif
38
39 #ifdef BSD_SYSTEM
40 #include <sys/ioctl.h>
41 #endif
42
43 #include "lisp.h"
44 #include "commands.h"
45 #include "intervals.h"
46 #include "buffer.h"
47
48 #include "systty.h"
49 #include "blockinput.h"
50 #include "syssignal.h"
51 #include "process.h"
52 #include "termhooks.h"
53 #include "keyboard.h"
54 #include "keymap.h"
55
56 #ifdef HAVE_SETLOCALE
57 #include <locale.h>
58 #endif
59
60 #ifdef HAVE_SETRLIMIT
61 #include <sys/time.h>
62 #include <sys/resource.h>
63 #endif
64
65 #ifndef O_RDWR
66 #define O_RDWR 2
67 #endif
68
69 #ifdef HAVE_SETPGID
70 #if !defined (USG) || defined (BSD_PGRPS)
71 #undef setpgrp
72 #define setpgrp setpgid
73 #endif
74 #endif
75
76 extern void malloc_warning P_ ((char *));
77 extern void set_time_zone_rule P_ ((char *));
78 #ifdef HAVE_INDEX
79 extern char *index P_ ((const char *, int));
80 #endif
81
82 /* Make these values available in GDB, which doesn't see macros. */
83
84 EMACS_INT gdb_valbits = VALBITS;
85 EMACS_INT gdb_gctypebits = GCTYPEBITS;
86 EMACS_INT gdb_emacs_intbits = sizeof (EMACS_INT) * BITS_PER_CHAR;
87 #ifdef DATA_SEG_BITS
88 EMACS_INT gdb_data_seg_bits = DATA_SEG_BITS;
89 #else
90 EMACS_INT gdb_data_seg_bits = 0;
91 #endif
92 EMACS_INT PVEC_FLAG = PSEUDOVECTOR_FLAG;
93
94 /* Command line args from shell, as list of strings. */
95 Lisp_Object Vcommand_line_args;
96
97 /* The name under which Emacs was invoked, with any leading directory
98 names discarded. */
99 Lisp_Object Vinvocation_name;
100
101 /* The directory name from which Emacs was invoked. */
102 Lisp_Object Vinvocation_directory;
103
104 /* The directory name in which to find subdirs such as lisp and etc.
105 nil means get them only from PATH_LOADSEARCH. */
106 Lisp_Object Vinstallation_directory;
107
108 /* Hook run by `kill-emacs' before it does really anything. */
109 Lisp_Object Vkill_emacs_hook;
110
111 /* An empty lisp string. To avoid having to build any other. */
112 Lisp_Object empty_string;
113
114 #ifdef SIGUSR1
115 /* Hooks for signal USR1 and USR2 handling. */
116 Lisp_Object Vsignal_USR1_hook;
117 #ifdef SIGUSR2
118 Lisp_Object Vsignal_USR2_hook;
119 #endif
120 #endif
121
122 /* Search path separator. */
123 Lisp_Object Vpath_separator;
124
125 /* Set nonzero after Emacs has started up the first time.
126 Prevents reinitialization of the Lisp world and keymaps
127 on subsequent starts. */
128 int initialized;
129
130 #ifdef DOUG_LEA_MALLOC
131 /* Preserves a pointer to the memory allocated that copies that
132 static data inside glibc's malloc. */
133 void *malloc_state_ptr;
134 /* From glibc, a routine that returns a copy of the malloc internal state. */
135 extern void *malloc_get_state ();
136 /* From glibc, a routine that overwrites the malloc internal state. */
137 extern void malloc_set_state ();
138 /* Non-zero if the MALLOC_CHECK_ enviroment variable was set while
139 dumping. Used to work around a bug in glibc's malloc. */
140 int malloc_using_checking;
141 #endif
142
143 /* Variable whose value is symbol giving operating system type. */
144 Lisp_Object Vsystem_type;
145
146 /* Variable whose value is string giving configuration built for. */
147 Lisp_Object Vsystem_configuration;
148
149 /* Variable whose value is string giving configuration options,
150 for use when reporting bugs. */
151 Lisp_Object Vsystem_configuration_options;
152
153 Lisp_Object Qfile_name_handler_alist;
154
155 /* Current and previous system locales for messages and time. */
156 Lisp_Object Vsystem_messages_locale;
157 Lisp_Object Vprevious_system_messages_locale;
158 Lisp_Object Vsystem_time_locale;
159 Lisp_Object Vprevious_system_time_locale;
160
161 /* If non-zero, emacs should not attempt to use an window-specific code,
162 but instead should use the virtual terminal under which it was started. */
163 int inhibit_window_system;
164
165 /* If nonzero, set Emacs to run at this priority. This is also used
166 in child_setup and sys_suspend to make sure subshells run at normal
167 priority; those functions have their own extern declaration. */
168 int emacs_priority;
169
170 /* If non-zero, a filter or a sentinel is running. Tested to save the match
171 data on the first attempt to change it inside asynchronous code. */
172 int running_asynch_code;
173
174 #ifdef BSD_PGRPS
175 /* See sysdep.c. */
176 extern int inherited_pgroup;
177 #endif
178
179 #ifdef HAVE_X_WINDOWS
180 /* If non-zero, -d was specified, meaning we're using some window system. */
181 int display_arg;
182 #endif
183
184 /* An address near the bottom of the stack.
185 Tells GC how to save a copy of the stack. */
186 char *stack_bottom;
187
188 #ifdef HAVE_WINDOW_SYSTEM
189 extern Lisp_Object Vwindow_system;
190 #endif /* HAVE_WINDOW_SYSTEM */
191
192 extern Lisp_Object Vauto_save_list_file_name;
193
194 #ifdef USG_SHARED_LIBRARIES
195 /* If nonzero, this is the place to put the end of the writable segment
196 at startup. */
197
198 unsigned int bss_end = 0;
199 #endif
200
201 /* Nonzero means running Emacs without interactive terminal. */
202
203 int noninteractive;
204
205 /* Value of Lisp variable `noninteractive'.
206 Normally same as C variable `noninteractive'
207 but nothing terrible happens if user sets this one. */
208
209 int noninteractive1;
210
211 /* Save argv and argc. */
212 char **initial_argv;
213 int initial_argc;
214
215 static void sort_args ();
216 void syms_of_emacs ();
217
218 #define USAGE1 "\
219 Usage: %s [OPTION-OR-FILENAME]...\n\
220 \n\
221 Run Emacs, the extensible, customizable, self-documenting real-time\n\
222 display editor. The recommended way to start Emacs for normal editing\n\
223 is with no options at all.\n\
224 \n\
225 Run M-x info RET m emacs RET m command arguments RET inside Emacs to\n\
226 read the main documentation for these command-line arguments.\n\
227 \n\
228 Initialization options:\n\
229 \n\
230 --batch do not do interactive display; implies -q\n\
231 --debug-init enable Emacs Lisp debugger during init file\n\
232 --help display this help message and exit\n\
233 --multibyte, --no-unibyte run Emacs in multibyte mode\n\
234 --no-init-file, -q load neither ~/.emacs nor default.el\n\
235 --no-shared-memory, -nl do not use shared memory\n\
236 --no-site-file do not load site-start.el\n\
237 --no-window-system, -nw don't communicate with X, ignoring $DISPLAY\n\
238 --terminal, -t DEVICE use DEVICE for terminal I/O\n\
239 --unibyte, --no-multibyte run Emacs in unibyte mode\n\
240 --user, -u USER load ~USER/.emacs instead of your own\n\
241 --version display version information and exit\n\
242 \n\
243 Action options:\n\
244 \n\
245 FILE visit FILE using find-file\n\
246 +LINE FILE visit FILE using find-file, then go to line LINE\n\
247 +LINE:COLUMN FILE visit FILE using find-file, then go to line LINE,\n\
248 column COLUMN\n\
249 --directory, -L DIR add DIR to variable load-path\n\
250 --eval EXPR evaluate Emacs Lisp expression EXPR\n\
251 --execute EXPR evaluate Emacs Lisp expression EXPR\n\
252 --find-file FILE visit FILE\n\
253 --funcall, -f FUNC call Emacs function FUNC with no arguments\n\
254 --insert FILE insert contents of FILE into current buffer\n\
255 --kill exit without asking for confirmation\n\
256 --load, -l FILE load FILE of Emacs Lisp code using the load function\n\
257 --visit FILE visit FILE\n\
258 \n"
259
260 #define USAGE2 "\
261 Display options:\n\
262 \n\
263 --background-color, -bg COLOR window background color\n\
264 --border-color, -bd COLOR main border color\n\
265 --border-width, -bw WIDTH width of main border\n\
266 --color=MODE color mode for character terminals;\n\
267 MODE defaults to `auto', and can also\n\
268 be `never', `auto', `always',\n\
269 or a mode name like `ansi8'\n\
270 --cursor-color, -cr COLOR color of the Emacs cursor indicating point\n\
271 --display, -d DISPLAY use X server DISPLAY\n\
272 --font, -fn FONT default font; must be fixed-width\n\
273 --foreground-color, -fg COLOR window foreground color\n\
274 --fullscreen, -fs make first frame fullscreen\n\
275 --fullwidth, -fw make the first frame wide as the screen\n\
276 --fullheight, -fh make the first frame high as the screen\n\
277 --geometry, -g GEOMETRY window geometry\n\
278 --iconic start Emacs in iconified state\n\
279 --icon-type, -i use picture of gnu for Emacs icon\n\
280 --internal-border, -ib WIDTH width between text and main border\n\
281 --line-spacing, -lsp PIXELS additional space to put between lines\n\
282 --mouse-color, -ms COLOR mouse cursor color in Emacs window\n\
283 --name NAME title of main Emacs window\n\
284 --reverse-video, -r, -rv switch foreground and background\n\
285 --title, -T, -wn TITLE title for Emacs windows\n\
286 --vertical-scroll-bars, -vb enable vertical scroll bars\n\
287 --xrm XRESOURCES set additional X resources\n\
288 \n\
289 You can generally also specify long option names with a single -; for\n\
290 example, -batch as well as --batch. You can use any unambiguous\n\
291 abbreviation for a --option.\n\
292 \n\
293 Various environment variables and window system resources also affect\n\
294 Emacs' operation. See the main documentation.\n\
295 \n"
296
297 #define USAGE3 "\
298 Report bugs to %s. First, please see the Bugs\n\
299 section of the Emacs manual or the file BUGS.\n"
300
301 \f
302 /* Signal code for the fatal signal that was received. */
303 int fatal_error_code;
304
305 /* Nonzero if handling a fatal error already. */
306 int fatal_error_in_progress;
307
308 /* If non-null, call this function from fatal_error_signal before
309 committing suicide. */
310
311 void (*fatal_error_signal_hook) P_ ((void));
312
313
314 #ifdef SIGUSR1
315 SIGTYPE
316 handle_USR1_signal (sig)
317 int sig;
318 {
319 struct input_event buf;
320
321 bzero (&buf, sizeof buf);
322 buf.kind = USER_SIGNAL_EVENT;
323 buf.frame_or_window = selected_frame;
324
325 kbd_buffer_store_event (&buf);
326 }
327 #endif /* SIGUSR1 */
328
329 #ifdef SIGUSR2
330 SIGTYPE
331 handle_USR2_signal (sig)
332 int sig;
333 {
334 struct input_event buf;
335
336 bzero (&buf, sizeof buf);
337 buf.kind = USER_SIGNAL_EVENT;
338 buf.code = 1;
339 buf.frame_or_window = selected_frame;
340
341 kbd_buffer_store_event (&buf);
342 }
343 #endif /* SIGUSR2 */
344
345 /* Handle bus errors, invalid instruction, etc. */
346 SIGTYPE
347 fatal_error_signal (sig)
348 int sig;
349 {
350 fatal_error_code = sig;
351 signal (sig, SIG_DFL);
352
353 TOTALLY_UNBLOCK_INPUT;
354
355 /* If fatal error occurs in code below, avoid infinite recursion. */
356 if (! fatal_error_in_progress)
357 {
358 fatal_error_in_progress = 1;
359
360 shut_down_emacs (sig, 0, Qnil);
361 }
362
363 #ifdef VMS
364 LIB$STOP (SS$_ABORT);
365 #else
366 /* Signal the same code; this time it will really be fatal.
367 Remember that since we're in a signal handler, the signal we're
368 going to send is probably blocked, so we have to unblock it if we
369 want to really receive it. */
370 #ifndef MSDOS
371 sigunblock (sigmask (fatal_error_code));
372 #endif
373
374 if (fatal_error_signal_hook)
375 fatal_error_signal_hook ();
376
377 kill (getpid (), fatal_error_code);
378 #endif /* not VMS */
379 }
380
381 #ifdef SIGDANGER
382
383 /* Handler for SIGDANGER. */
384 SIGTYPE
385 memory_warning_signal (sig)
386 int sig;
387 {
388 signal (sig, memory_warning_signal);
389
390 malloc_warning ("Operating system warns that virtual memory is running low.\n");
391
392 /* It might be unsafe to call do_auto_save now. */
393 force_auto_save_soon ();
394 }
395 #endif
396
397 /* We define abort, rather than using it from the library,
398 so that GDB can return from a breakpoint here.
399 MSDOS has its own definition in msdos.c. */
400
401 #if ! defined (DOS_NT) && ! defined (NO_ABORT)
402
403 #ifndef ABORT_RETURN_TYPE
404 #define ABORT_RETURN_TYPE void
405 #endif
406
407 ABORT_RETURN_TYPE
408 abort ()
409 {
410 kill (getpid (), SIGABRT);
411 /* This shouldn't be executed, but it prevents a warning. */
412 exit (1);
413 }
414 #endif
415
416 \f
417 /* Code for dealing with Lisp access to the Unix command line. */
418
419 static void
420 init_cmdargs (argc, argv, skip_args)
421 int argc;
422 char **argv;
423 int skip_args;
424 {
425 register int i;
426 Lisp_Object name, dir, tem;
427 int count = specpdl_ptr - specpdl;
428 Lisp_Object raw_name;
429
430 initial_argv = argv;
431 initial_argc = argc;
432
433 raw_name = build_string (argv[0]);
434
435 /* Add /: to the front of the name
436 if it would otherwise be treated as magic. */
437 tem = Ffind_file_name_handler (raw_name, Qt);
438 if (! NILP (tem))
439 raw_name = concat2 (build_string ("/:"), raw_name);
440
441 Vinvocation_name = Ffile_name_nondirectory (raw_name);
442 Vinvocation_directory = Ffile_name_directory (raw_name);
443
444 /* If we got no directory in argv[0], search PATH to find where
445 Emacs actually came from. */
446 if (NILP (Vinvocation_directory))
447 {
448 Lisp_Object found;
449 int yes = openp (Vexec_path, Vinvocation_name,
450 Vexec_suffixes, &found, 1);
451 if (yes == 1)
452 {
453 /* Add /: to the front of the name
454 if it would otherwise be treated as magic. */
455 tem = Ffind_file_name_handler (found, Qt);
456 if (! NILP (tem))
457 found = concat2 (build_string ("/:"), found);
458 Vinvocation_directory = Ffile_name_directory (found);
459 }
460 }
461
462 if (!NILP (Vinvocation_directory)
463 && NILP (Ffile_name_absolute_p (Vinvocation_directory)))
464 /* Emacs was started with relative path, like ./emacs.
465 Make it absolute. */
466 Vinvocation_directory = Fexpand_file_name (Vinvocation_directory, Qnil);
467
468 Vinstallation_directory = Qnil;
469
470 if (!NILP (Vinvocation_directory))
471 {
472 dir = Vinvocation_directory;
473 name = Fexpand_file_name (Vinvocation_name, dir);
474 while (1)
475 {
476 Lisp_Object tem, lib_src_exists;
477 Lisp_Object etc_exists, info_exists;
478
479 /* See if dir contains subdirs for use by Emacs.
480 Check for the ones that would exist in a build directory,
481 not including lisp and info. */
482 tem = Fexpand_file_name (build_string ("lib-src"), dir);
483 lib_src_exists = Ffile_exists_p (tem);
484
485 #ifdef MSDOS
486 /* MSDOS installations frequently remove lib-src, but we still
487 must set installation-directory, or else info won't find
488 its files (it uses the value of installation-directory). */
489 tem = Fexpand_file_name (build_string ("info"), dir);
490 info_exists = Ffile_exists_p (tem);
491 #else
492 info_exists = Qnil;
493 #endif
494
495 if (!NILP (lib_src_exists) || !NILP (info_exists))
496 {
497 tem = Fexpand_file_name (build_string ("etc"), dir);
498 etc_exists = Ffile_exists_p (tem);
499 if (!NILP (etc_exists))
500 {
501 Vinstallation_directory
502 = Ffile_name_as_directory (dir);
503 break;
504 }
505 }
506
507 /* See if dir's parent contains those subdirs. */
508 tem = Fexpand_file_name (build_string ("../lib-src"), dir);
509 lib_src_exists = Ffile_exists_p (tem);
510
511
512 #ifdef MSDOS
513 /* See the MSDOS commentary above. */
514 tem = Fexpand_file_name (build_string ("../info"), dir);
515 info_exists = Ffile_exists_p (tem);
516 #else
517 info_exists = Qnil;
518 #endif
519
520 if (!NILP (lib_src_exists) || !NILP (info_exists))
521 {
522 tem = Fexpand_file_name (build_string ("../etc"), dir);
523 etc_exists = Ffile_exists_p (tem);
524 if (!NILP (etc_exists))
525 {
526 tem = Fexpand_file_name (build_string (".."), dir);
527 Vinstallation_directory
528 = Ffile_name_as_directory (tem);
529 break;
530 }
531 }
532
533 /* If the Emacs executable is actually a link,
534 next try the dir that the link points into. */
535 tem = Ffile_symlink_p (name);
536 if (!NILP (tem))
537 {
538 name = Fexpand_file_name (tem, dir);
539 dir = Ffile_name_directory (name);
540 }
541 else
542 break;
543 }
544 }
545
546 Vcommand_line_args = Qnil;
547
548 for (i = argc - 1; i >= 0; i--)
549 {
550 if (i == 0 || i > skip_args)
551 Vcommand_line_args
552 = Fcons (build_string (argv[i]), Vcommand_line_args);
553 }
554
555 unbind_to (count, Qnil);
556 }
557
558 DEFUN ("invocation-name", Finvocation_name, Sinvocation_name, 0, 0, 0,
559 doc: /* Return the program name that was used to run Emacs.
560 Any directory names are omitted. */)
561 ()
562 {
563 return Fcopy_sequence (Vinvocation_name);
564 }
565
566 DEFUN ("invocation-directory", Finvocation_directory, Sinvocation_directory,
567 0, 0, 0,
568 doc: /* Return the directory name in which the Emacs executable was located. */)
569 ()
570 {
571 return Fcopy_sequence (Vinvocation_directory);
572 }
573
574 \f
575 #ifdef VMS
576 #ifdef LINK_CRTL_SHARE
577 #ifdef SHARABLE_LIB_BUG
578 extern noshare char **environ;
579 #endif /* SHARABLE_LIB_BUG */
580 #endif /* LINK_CRTL_SHARE */
581 #endif /* VMS */
582
583 #ifdef HAVE_TZSET
584 /* A valid but unlikely value for the TZ environment value.
585 It is OK (though a bit slower) if the user actually chooses this value. */
586 static char dump_tz[] = "UtC0";
587 #endif
588
589 #ifndef ORDINARY_LINK
590 /* We don't include crtbegin.o and crtend.o in the link,
591 so these functions and variables might be missed.
592 Provide dummy definitions to avoid error.
593 (We don't have any real constructors or destructors.) */
594 #ifdef __GNUC__
595 #ifndef GCC_CTORS_IN_LIBC
596 void __do_global_ctors ()
597 {}
598 void __do_global_ctors_aux ()
599 {}
600 void __do_global_dtors ()
601 {}
602 /* Linux has a bug in its library; avoid an error. */
603 #ifndef GNU_LINUX
604 char * __CTOR_LIST__[2] = { (char *) (-1), 0 };
605 #endif
606 char * __DTOR_LIST__[2] = { (char *) (-1), 0 };
607 #endif /* GCC_CTORS_IN_LIBC */
608 void __main ()
609 {}
610 #endif /* __GNUC__ */
611 #endif /* ORDINARY_LINK */
612
613 /* Test whether the next argument in ARGV matches SSTR or a prefix of
614 LSTR (at least MINLEN characters). If so, then if VALPTR is non-null
615 (the argument is supposed to have a value) store in *VALPTR either
616 the next argument or the portion of this one after the equal sign.
617 ARGV is read starting at position *SKIPPTR; this index is advanced
618 by the number of arguments used.
619
620 Too bad we can't just use getopt for all of this, but we don't have
621 enough information to do it right. */
622
623 static int
624 argmatch (argv, argc, sstr, lstr, minlen, valptr, skipptr)
625 char **argv;
626 int argc;
627 char *sstr;
628 char *lstr;
629 int minlen;
630 char **valptr;
631 int *skipptr;
632 {
633 char *p = NULL;
634 int arglen;
635 char *arg;
636
637 /* Don't access argv[argc]; give up in advance. */
638 if (argc <= *skipptr + 1)
639 return 0;
640
641 arg = argv[*skipptr+1];
642 if (arg == NULL)
643 return 0;
644 if (strcmp (arg, sstr) == 0)
645 {
646 if (valptr != NULL)
647 {
648 *valptr = argv[*skipptr+2];
649 *skipptr += 2;
650 }
651 else
652 *skipptr += 1;
653 return 1;
654 }
655 arglen = (valptr != NULL && (p = index (arg, '=')) != NULL
656 ? p - arg : strlen (arg));
657 if (lstr == 0 || arglen < minlen || strncmp (arg, lstr, arglen) != 0)
658 return 0;
659 else if (valptr == NULL)
660 {
661 *skipptr += 1;
662 return 1;
663 }
664 else if (p != NULL)
665 {
666 *valptr = p+1;
667 *skipptr += 1;
668 return 1;
669 }
670 else if (argv[*skipptr+2] != NULL)
671 {
672 *valptr = argv[*skipptr+2];
673 *skipptr += 2;
674 return 1;
675 }
676 else
677 {
678 return 0;
679 }
680 }
681
682 #ifdef DOUG_LEA_MALLOC
683
684 /* malloc can be invoked even before main (e.g. by the dynamic
685 linker), so the dumped malloc state must be restored as early as
686 possible using this special hook. */
687
688 static void
689 malloc_initialize_hook ()
690 {
691 #ifndef USE_CRT_DLL
692 extern char **environ;
693 #endif
694
695 if (initialized)
696 {
697 if (!malloc_using_checking)
698 /* Work around a bug in glibc's malloc. MALLOC_CHECK_ must be
699 ignored if the heap to be restored was constructed without
700 malloc checking. Can't use unsetenv, since that calls malloc. */
701 {
702 char **p;
703
704 for (p = environ; p && *p; p++)
705 if (strncmp (*p, "MALLOC_CHECK_=", 14) == 0)
706 {
707 do
708 *p = p[1];
709 while (*++p);
710 break;
711 }
712 }
713
714 malloc_set_state (malloc_state_ptr);
715 free (malloc_state_ptr);
716 }
717 else
718 malloc_using_checking = getenv ("MALLOC_CHECK_") != NULL;
719 }
720
721 void (*__malloc_initialize_hook) () = malloc_initialize_hook;
722
723 #endif /* DOUG_LEA_MALLOC */
724
725
726 #define REPORT_EMACS_BUG_ADDRESS "bug-gnu-emacs@gnu.org"
727 #define REPORT_EMACS_BUG_PRETEST_ADDRESS "emacs-pretest-bug@gnu.org"
728
729 /* This function is used to determine an address to which bug report should
730 be sent. */
731
732 char *
733 bug_reporting_address ()
734 {
735 int count = 0;
736 Lisp_Object temp;
737 char *string;
738
739 temp = Fsymbol_value (intern ("emacs-version"));
740
741 /* When `emacs-version' is invalid, use normal address. */
742 if (!STRINGP(temp))
743 return REPORT_EMACS_BUG_ADDRESS;
744
745 string = XSTRING (temp)->data;
746
747 /* Count dots in `emacs-version'. */
748 while (*string)
749 {
750 if (*string == '.')
751 count++;
752 string++;
753 }
754
755 /* When `emacs-version' has at least three dots, it is development or
756 pretest version of Emacs. */
757 return count >= 3 ? REPORT_EMACS_BUG_PRETEST_ADDRESS : REPORT_EMACS_BUG_ADDRESS;
758 }
759
760
761 /* ARGSUSED */
762 int
763 main (argc, argv, envp)
764 int argc;
765 char **argv;
766 char **envp;
767 {
768 #if GC_MARK_STACK
769 Lisp_Object dummy;
770 #endif
771 char stack_bottom_variable;
772 int do_initial_setlocale;
773 int skip_args = 0;
774 #ifndef USE_CRT_DLL
775 extern int errno;
776 #endif
777 #ifdef HAVE_SETRLIMIT
778 struct rlimit rlim;
779 #endif
780 int no_loadup = 0;
781
782 #if GC_MARK_STACK
783 extern Lisp_Object *stack_base;
784 stack_base = &dummy;
785 #endif
786
787 #ifdef LINUX_SBRK_BUG
788 __sbrk (1);
789 #endif
790
791 #ifdef RUN_TIME_REMAP
792 if (initialized)
793 run_time_remap (argv[0]);
794 #endif
795
796 sort_args (argc, argv);
797 argc = 0;
798 while (argv[argc]) argc++;
799
800 if (argmatch (argv, argc, "-version", "--version", 3, NULL, &skip_args)
801 /* We don't know the version number unless this is a dumped Emacs.
802 So ignore --version otherwise. */
803 && initialized)
804 {
805 Lisp_Object tem;
806 tem = Fsymbol_value (intern ("emacs-version"));
807 if (!STRINGP (tem))
808 {
809 fprintf (stderr, "Invalid value of `emacs-version'\n");
810 exit (1);
811 }
812 else
813 {
814 printf ("GNU Emacs %s\n", XSTRING (tem)->data);
815 printf ("Copyright (C) 2001 Free Software Foundation, Inc.\n");
816 printf ("GNU Emacs comes with ABSOLUTELY NO WARRANTY.\n");
817 printf ("You may redistribute copies of Emacs\n");
818 printf ("under the terms of the GNU General Public License.\n");
819 printf ("For more information about these matters, ");
820 printf ("see the file named COPYING.\n");
821 exit (0);
822 }
823 }
824
825 /* Map in shared memory, if we are using that. */
826 #ifdef HAVE_SHM
827 if (argmatch (argv, argc, "-nl", "--no-shared-memory", 6, NULL, &skip_args))
828 {
829 map_in_data (0);
830 /* The shared memory was just restored, which clobbered this. */
831 skip_args = 1;
832 }
833 else
834 {
835 map_in_data (1);
836 /* The shared memory was just restored, which clobbered this. */
837 skip_args = 0;
838 }
839 #endif
840
841 #ifdef NeXT
842 {
843 extern int malloc_cookie;
844 /* This helps out unexnext.c. */
845 if (initialized)
846 if (malloc_jumpstart (malloc_cookie) != 0)
847 printf ("malloc jumpstart failed!\n");
848 }
849 #endif /* NeXT */
850
851 #ifdef VMS
852 /* If -map specified, map the data file in. */
853 {
854 char *file;
855 if (argmatch (argv, argc, "-map", "--map-data", 3, &mapin_file, &skip_args))
856 mapin_data (file);
857 }
858
859 #ifdef LINK_CRTL_SHARE
860 #ifdef SHARABLE_LIB_BUG
861 /* Bletcherous shared libraries! */
862 if (!stdin)
863 stdin = fdopen (0, "r");
864 if (!stdout)
865 stdout = fdopen (1, "w");
866 if (!stderr)
867 stderr = fdopen (2, "w");
868 if (!environ)
869 environ = envp;
870 #endif /* SHARABLE_LIB_BUG */
871 #endif /* LINK_CRTL_SHARE */
872 #endif /* VMS */
873
874 #if defined (HAVE_SETRLIMIT) && defined (RLIMIT_STACK)
875 /* Extend the stack space available.
876 Don't do that if dumping, since some systems (e.g. DJGPP)
877 might define a smaller stack limit at that time. */
878 if (1
879 #ifndef CANNOT_DUMP
880 && (!noninteractive || initialized)
881 #endif
882 && !getrlimit (RLIMIT_STACK, &rlim))
883 {
884 long newlim;
885 extern int re_max_failures;
886 /* Approximate the amount regex.c needs per unit of re_max_failures. */
887 int ratio = 20 * sizeof (char *);
888 /* Then add 33% to cover the size of the smaller stacks that regex.c
889 successively allocates and discards, on its way to the maximum. */
890 ratio += ratio / 3;
891 /* Add in some extra to cover
892 what we're likely to use for other reasons. */
893 newlim = re_max_failures * ratio + 200000;
894 #ifdef __NetBSD__
895 /* NetBSD (at least NetBSD 1.2G and former) has a bug in its
896 stack allocation routine for new process that the allocation
897 fails if stack limit is not on page boundary. So, round up the
898 new limit to page boundary. */
899 newlim = (newlim + getpagesize () - 1) / getpagesize () * getpagesize();
900 #endif
901 if (newlim > rlim.rlim_max)
902 {
903 newlim = rlim.rlim_max;
904 /* Don't let regex.c overflow the stack we have. */
905 re_max_failures = (newlim - 200000) / ratio;
906 }
907 if (rlim.rlim_cur < newlim)
908 rlim.rlim_cur = newlim;
909
910 setrlimit (RLIMIT_STACK, &rlim);
911 }
912 #endif /* HAVE_SETRLIMIT and RLIMIT_STACK */
913
914 /* Record (approximately) where the stack begins. */
915 stack_bottom = &stack_bottom_variable;
916
917 #ifdef USG_SHARED_LIBRARIES
918 if (bss_end)
919 brk ((void *)bss_end);
920 #endif
921
922 clearerr (stdin);
923
924 #ifndef SYSTEM_MALLOC
925 /* Arrange to get warning messages as memory fills up. */
926 memory_warnings (0, malloc_warning);
927
928 /* Call malloc at least once, to run the initial __malloc_hook.
929 Also call realloc and free for consistency. */
930 free (realloc (malloc (4), 4));
931
932 /* Arrange to disable interrupt input inside malloc etc. */
933 uninterrupt_malloc ();
934 #endif /* not SYSTEM_MALLOC */
935
936 #ifdef MSDOS
937 /* We do all file input/output as binary files. When we need to translate
938 newlines, we do that manually. */
939 _fmode = O_BINARY;
940
941 #if __DJGPP__ >= 2
942 if (!isatty (fileno (stdin)))
943 setmode (fileno (stdin), O_BINARY);
944 if (!isatty (fileno (stdout)))
945 {
946 fflush (stdout);
947 setmode (fileno (stdout), O_BINARY);
948 }
949 #else /* not __DJGPP__ >= 2 */
950 (stdin)->_flag &= ~_IOTEXT;
951 (stdout)->_flag &= ~_IOTEXT;
952 (stderr)->_flag &= ~_IOTEXT;
953 #endif /* not __DJGPP__ >= 2 */
954 #endif /* MSDOS */
955
956 #ifdef SET_EMACS_PRIORITY
957 if (emacs_priority)
958 nice (emacs_priority);
959 setuid (getuid ());
960 #endif /* SET_EMACS_PRIORITY */
961
962 /* Skip initial setlocale if LC_ALL is "C", as it's not needed in that case.
963 The build procedure uses this while dumping, to ensure that the
964 dumped Emacs does not have its system locale tables initialized,
965 as that might cause screwups when the dumped Emacs starts up. */
966 {
967 char *lc_all = getenv ("LC_ALL");
968 do_initial_setlocale = ! lc_all || strcmp (lc_all, "C");
969 }
970
971 /* Set locale now, so that initial error messages are localized properly.
972 fixup_locale must wait until later, since it builds strings. */
973 if (do_initial_setlocale)
974 setlocale (LC_ALL, "");
975
976 #ifdef EXTRA_INITIALIZE
977 EXTRA_INITIALIZE;
978 #endif
979
980 inhibit_window_system = 0;
981
982 /* Handle the -t switch, which specifies filename to use as terminal. */
983 while (1)
984 {
985 char *term;
986 if (argmatch (argv, argc, "-t", "--terminal", 4, &term, &skip_args))
987 {
988 int result;
989 emacs_close (0);
990 emacs_close (1);
991 result = emacs_open (term, O_RDWR, 0);
992 if (result < 0)
993 {
994 char *errstring = strerror (errno);
995 fprintf (stderr, "%s: %s: %s\n", argv[0], term, errstring);
996 exit (1);
997 }
998 dup (0);
999 if (! isatty (0))
1000 {
1001 fprintf (stderr, "%s: %s: not a tty\n", argv[0], term);
1002 exit (1);
1003 }
1004 fprintf (stderr, "Using %s\n", term);
1005 #ifdef HAVE_WINDOW_SYSTEM
1006 inhibit_window_system = 1; /* -t => -nw */
1007 #endif
1008 }
1009 else
1010 break;
1011 }
1012
1013 /* Command line option --no-windows is deprecated and thus not mentioned
1014 in the manual and usage informations. */
1015 if (argmatch (argv, argc, "-nw", "--no-window-system", 6, NULL, &skip_args)
1016 || argmatch (argv, argc, "-nw", "--no-windows", 6, NULL, &skip_args))
1017 inhibit_window_system = 1;
1018
1019 /* Handle the -batch switch, which means don't do interactive display. */
1020 noninteractive = 0;
1021 if (argmatch (argv, argc, "-batch", "--batch", 5, NULL, &skip_args))
1022 noninteractive = 1;
1023
1024 /* Handle the --help option, which gives a usage message. */
1025 if (argmatch (argv, argc, "-help", "--help", 3, NULL, &skip_args))
1026 {
1027 printf (USAGE1, argv[0]);
1028 printf (USAGE2);
1029 printf (USAGE3, bug_reporting_address ());
1030 exit (0);
1031 }
1032
1033 if (! noninteractive)
1034 {
1035 #ifdef BSD_PGRPS
1036 if (initialized)
1037 {
1038 inherited_pgroup = EMACS_GETPGRP (0);
1039 setpgrp (0, getpid ());
1040 }
1041 #else
1042 #if defined (USG5) && defined (INTERRUPT_INPUT)
1043 setpgrp ();
1044 #endif
1045 #endif
1046 }
1047
1048 init_signals ();
1049
1050 /* Don't catch SIGHUP if dumping. */
1051 if (1
1052 #ifndef CANNOT_DUMP
1053 && initialized
1054 #endif
1055 )
1056 {
1057 sigblock (sigmask (SIGHUP));
1058 /* In --batch mode, don't catch SIGHUP if already ignored.
1059 That makes nohup work. */
1060 if (! noninteractive
1061 || signal (SIGHUP, SIG_IGN) != SIG_IGN)
1062 signal (SIGHUP, fatal_error_signal);
1063 sigunblock (sigmask (SIGHUP));
1064 }
1065
1066 if (
1067 #ifndef CANNOT_DUMP
1068 ! noninteractive || initialized
1069 #else
1070 1
1071 #endif
1072 )
1073 {
1074 /* Don't catch these signals in batch mode if dumping.
1075 On some machines, this sets static data that would make
1076 signal fail to work right when the dumped Emacs is run. */
1077 signal (SIGQUIT, fatal_error_signal);
1078 signal (SIGILL, fatal_error_signal);
1079 signal (SIGTRAP, fatal_error_signal);
1080 #ifdef SIGUSR1
1081 signal (SIGUSR1, handle_USR1_signal);
1082 #ifdef SIGUSR2
1083 signal (SIGUSR2, handle_USR2_signal);
1084 #endif
1085 #endif
1086 #ifdef SIGABRT
1087 signal (SIGABRT, fatal_error_signal);
1088 #endif
1089 #ifdef SIGHWE
1090 signal (SIGHWE, fatal_error_signal);
1091 #endif
1092 #ifdef SIGPRE
1093 signal (SIGPRE, fatal_error_signal);
1094 #endif
1095 #ifdef SIGORE
1096 signal (SIGORE, fatal_error_signal);
1097 #endif
1098 #ifdef SIGUME
1099 signal (SIGUME, fatal_error_signal);
1100 #endif
1101 #ifdef SIGDLK
1102 signal (SIGDLK, fatal_error_signal);
1103 #endif
1104 #ifdef SIGCPULIM
1105 signal (SIGCPULIM, fatal_error_signal);
1106 #endif
1107 #ifdef SIGIOT
1108 /* This is missing on some systems - OS/2, for example. */
1109 signal (SIGIOT, fatal_error_signal);
1110 #endif
1111 #ifdef SIGEMT
1112 signal (SIGEMT, fatal_error_signal);
1113 #endif
1114 signal (SIGFPE, fatal_error_signal);
1115 #ifdef SIGBUS
1116 signal (SIGBUS, fatal_error_signal);
1117 #endif
1118 signal (SIGSEGV, fatal_error_signal);
1119 #ifdef SIGSYS
1120 signal (SIGSYS, fatal_error_signal);
1121 #endif
1122 signal (SIGTERM, fatal_error_signal);
1123 #ifdef SIGXCPU
1124 signal (SIGXCPU, fatal_error_signal);
1125 #endif
1126 #ifdef SIGXFSZ
1127 signal (SIGXFSZ, fatal_error_signal);
1128 #endif /* SIGXFSZ */
1129
1130 #ifdef SIGDANGER
1131 /* This just means available memory is getting low. */
1132 signal (SIGDANGER, memory_warning_signal);
1133 #endif
1134
1135 #ifdef AIX
1136 /* 20 is SIGCHLD, 21 is SIGTTIN, 22 is SIGTTOU. */
1137 signal (SIGXCPU, fatal_error_signal);
1138 #ifndef _I386
1139 signal (SIGIOINT, fatal_error_signal);
1140 #endif
1141 signal (SIGGRANT, fatal_error_signal);
1142 signal (SIGRETRACT, fatal_error_signal);
1143 signal (SIGSOUND, fatal_error_signal);
1144 signal (SIGMSG, fatal_error_signal);
1145 #endif /* AIX */
1146 }
1147
1148 noninteractive1 = noninteractive;
1149
1150 /* Perform basic initializations (not merely interning symbols). */
1151
1152 if (!initialized)
1153 {
1154 init_alloc_once ();
1155 init_obarray ();
1156 init_eval_once ();
1157 init_character_once ();
1158 init_charset_once ();
1159 init_coding_once ();
1160 init_syntax_once (); /* Create standard syntax table. */
1161 init_category_once (); /* Create standard category table. */
1162 /* Must be done before init_buffer. */
1163 init_casetab_once ();
1164 init_buffer_once (); /* Create buffer table and some buffers. */
1165 init_minibuf_once (); /* Create list of minibuffers. */
1166 /* Must precede init_window_once. */
1167
1168 /* Call syms_of_xfaces before init_window_once because that
1169 function creates Vterminal_frame. Termcap frames now use
1170 faces, and the face implementation uses some symbols as
1171 face names. */
1172 syms_of_xfaces ();
1173 /* Call syms_of_keyboard before init_window_once because
1174 keyboard sets up symbols that include some face names that
1175 the X support will want to use. This can happen when
1176 CANNOT_DUMP is defined. */
1177 syms_of_keyboard ();
1178
1179 #ifdef macintosh
1180 /* init_window_once calls make_terminal_frame which on Mac OS
1181 creates a full-fledge output_mac type frame. This does not
1182 work correctly before syms_of_textprop, syms_of_macfns,
1183 syms_of_ccl, syms_of_fontset, syms_of_xterm, syms_of_search,
1184 syms_of_frame, x_term_init, and init_keyboard have already
1185 been called. */
1186 syms_of_textprop ();
1187 syms_of_macfns ();
1188 syms_of_ccl ();
1189 syms_of_fontset ();
1190 syms_of_macterm ();
1191 syms_of_macmenu ();
1192 syms_of_data ();
1193 syms_of_search ();
1194 syms_of_frame ();
1195
1196 x_term_init ();
1197 init_keyboard ();
1198 #endif
1199
1200 init_window_once (); /* Init the window system. */
1201 init_fileio_once (); /* Must precede any path manipulation. */
1202 }
1203
1204 init_alloc ();
1205
1206 if (do_initial_setlocale)
1207 {
1208 fixup_locale ();
1209 Vsystem_messages_locale = Vprevious_system_messages_locale;
1210 Vsystem_time_locale = Vprevious_system_time_locale;
1211 }
1212
1213 init_eval ();
1214 init_data ();
1215 #ifdef CLASH_DETECTION
1216 init_filelock ();
1217 #endif
1218 init_atimer ();
1219 running_asynch_code = 0;
1220
1221 /* Handle --unibyte and the EMACS_UNIBYTE envvar,
1222 but not while dumping. */
1223 if (
1224 #ifndef CANNOT_DUMP
1225 ! noninteractive || initialized
1226 #else
1227 1
1228 #endif
1229 )
1230 {
1231 int inhibit_unibyte = 0;
1232
1233 /* --multibyte overrides EMACS_UNIBYTE. */
1234 if (argmatch (argv, argc, "-no-unibyte", "--no-unibyte", 4, NULL, &skip_args)
1235 || argmatch (argv, argc, "-multibyte", "--multibyte", 4, NULL, &skip_args))
1236 inhibit_unibyte = 1;
1237
1238 /* --unibyte requests that we set up to do everything with single-byte
1239 buffers and strings. We need to handle this before calling
1240 init_lread, init_editfns and other places that generate Lisp strings
1241 from text in the environment. */
1242 /* Actually this shouldn't be needed as of 20.4 in a generally
1243 unibyte environment. As handa says, environment values
1244 aren't now decoded; also existing buffers are now made
1245 unibyte during startup if .emacs sets unibyte. Tested with
1246 8-bit data in environment variables and /etc/passwd, setting
1247 unibyte and Latin-1 in .emacs. -- Dave Love */
1248 if (argmatch (argv, argc, "-unibyte", "--unibyte", 4, NULL, &skip_args)
1249 || argmatch (argv, argc, "-no-multibyte", "--no-multibyte", 4, NULL, &skip_args)
1250 || (getenv ("EMACS_UNIBYTE") && !inhibit_unibyte))
1251 {
1252 Lisp_Object old_log_max;
1253 Lisp_Object symbol, tail;
1254
1255 symbol = intern ("default-enable-multibyte-characters");
1256 Fset (symbol, Qnil);
1257
1258 if (initialized)
1259 {
1260 /* Erase pre-dump messages in *Messages* now so no abort. */
1261 old_log_max = Vmessage_log_max;
1262 XSETFASTINT (Vmessage_log_max, 0);
1263 message_dolog ("", 0, 1, 0);
1264 Vmessage_log_max = old_log_max;
1265 }
1266
1267 for (tail = Vbuffer_alist; CONSP (tail);
1268 tail = XCDR (tail))
1269 {
1270 Lisp_Object buffer;
1271
1272 buffer = Fcdr (XCAR (tail));
1273 /* Make all multibyte buffers unibyte. */
1274 if (BUF_Z_BYTE (XBUFFER (buffer)) > BUF_Z (XBUFFER (buffer)))
1275 {
1276 struct buffer *current = current_buffer;
1277
1278 set_buffer_temp (XBUFFER (buffer));
1279 Fset_buffer_multibyte (Qnil, Qnil);
1280 set_buffer_temp (current);
1281 }
1282 }
1283 }
1284 }
1285
1286 no_loadup
1287 = argmatch (argv, argc, "-nl", "--no-loadup", 6, NULL, &skip_args);
1288
1289
1290 #ifdef HAVE_X_WINDOWS
1291 /* Stupid kludge to catch command-line display spec. We can't
1292 handle this argument entirely in window system dependent code
1293 because we don't even know which window system dependent code
1294 to run until we've recognized this argument. */
1295 {
1296 char *displayname = 0;
1297 int count_before = skip_args;
1298
1299 /* Skip any number of -d options, but only use the last one. */
1300 while (1)
1301 {
1302 int count_before_this = skip_args;
1303
1304 if (argmatch (argv, argc, "-d", "--display", 3, &displayname, &skip_args))
1305 display_arg = 1;
1306 else if (argmatch (argv, argc, "-display", 0, 3, &displayname, &skip_args))
1307 display_arg = 1;
1308 else
1309 break;
1310
1311 count_before = count_before_this;
1312 }
1313
1314 /* If we have the form --display=NAME,
1315 convert it into -d name.
1316 This requires inserting a new element into argv. */
1317 if (displayname != 0 && skip_args - count_before == 1)
1318 {
1319 char **new = (char **) xmalloc (sizeof (char *) * (argc + 2));
1320 int j;
1321
1322 for (j = 0; j < count_before + 1; j++)
1323 new[j] = argv[j];
1324 new[count_before + 1] = "-d";
1325 new[count_before + 2] = displayname;
1326 for (j = count_before + 2; j <argc; j++)
1327 new[j + 1] = argv[j];
1328 argv = new;
1329 argc++;
1330 }
1331 /* Change --display to -d, when its arg is separate. */
1332 else if (displayname != 0 && skip_args > count_before
1333 && argv[count_before + 1][1] == '-')
1334 argv[count_before + 1] = "-d";
1335
1336 /* Don't actually discard this arg. */
1337 skip_args = count_before;
1338 }
1339 #endif
1340
1341 /* argmatch must not be used after here,
1342 except when bulding temacs
1343 because the -d argument has not been skipped in skip_args. */
1344
1345 #ifdef MSDOS
1346 /* Call early 'cause init_environment needs it. */
1347 init_dosfns ();
1348 /* Set defaults for several environment variables. */
1349 if (initialized)
1350 init_environment (argc, argv, skip_args);
1351 else
1352 tzset ();
1353 #endif /* MSDOS */
1354
1355 #ifdef WINDOWSNT
1356 /* Initialize environment from registry settings. */
1357 init_environment (argv);
1358 init_ntproc (); /* must precede init_editfns. */
1359 #endif
1360
1361 /* egetenv is a pretty low-level facility, which may get called in
1362 many circumstances; it seems flimsy to put off initializing it
1363 until calling init_callproc. */
1364 set_process_environment ();
1365 /* AIX crashes are reported in system versions 3.2.3 and 3.2.4
1366 if this is not done. Do it after set_process_environment so that we
1367 don't pollute Vprocess_environment. */
1368 /* Setting LANG here will defeat the startup locale processing... */
1369 #ifdef AIX3_2
1370 putenv ("LANG=C");
1371 #endif
1372
1373 init_buffer (); /* Init default directory of main buffer. */
1374
1375 init_callproc_1 (); /* Must precede init_cmdargs and init_sys_modes. */
1376 init_cmdargs (argc, argv, skip_args); /* Must precede init_lread. */
1377
1378 if (initialized)
1379 {
1380 /* Erase any pre-dump messages in the message log, to avoid confusion. */
1381 Lisp_Object old_log_max;
1382 old_log_max = Vmessage_log_max;
1383 XSETFASTINT (Vmessage_log_max, 0);
1384 message_dolog ("", 0, 1, 0);
1385 Vmessage_log_max = old_log_max;
1386 }
1387
1388 init_callproc (); /* Must follow init_cmdargs but not init_sys_modes. */
1389 init_lread ();
1390 init_charset ();
1391
1392 /* Intern the names of all standard functions and variables;
1393 define standard keys. */
1394
1395 if (!initialized)
1396 {
1397 /* The basic levels of Lisp must come first. */
1398 /* And data must come first of all
1399 for the sake of symbols like error-message. */
1400 #ifndef macintosh
1401 /* Called before init_window_once for Mac OS. */
1402 syms_of_data ();
1403 #endif
1404 syms_of_alloc ();
1405 syms_of_chartab ();
1406 syms_of_lread ();
1407 syms_of_print ();
1408 syms_of_eval ();
1409 syms_of_fns ();
1410 syms_of_floatfns ();
1411
1412 syms_of_abbrev ();
1413 syms_of_buffer ();
1414 syms_of_bytecode ();
1415 syms_of_callint ();
1416 syms_of_casefiddle ();
1417 syms_of_casetab ();
1418 syms_of_callproc ();
1419 syms_of_category ();
1420 #ifndef macintosh
1421 /* Called before init_window_once for Mac OS. */
1422 syms_of_ccl ();
1423 #endif
1424 syms_of_character ();
1425 syms_of_charset ();
1426 syms_of_cmds ();
1427 #ifndef NO_DIR_LIBRARY
1428 syms_of_dired ();
1429 #endif /* not NO_DIR_LIBRARY */
1430 syms_of_display ();
1431 syms_of_doc ();
1432 syms_of_editfns ();
1433 syms_of_emacs ();
1434 syms_of_fileio ();
1435 syms_of_coding (); /* This should be after syms_of_fileio. */
1436 #ifdef CLASH_DETECTION
1437 syms_of_filelock ();
1438 #endif /* CLASH_DETECTION */
1439 syms_of_indent ();
1440 syms_of_insdel ();
1441 syms_of_keymap ();
1442 syms_of_macros ();
1443 syms_of_marker ();
1444 syms_of_minibuf ();
1445 syms_of_process ();
1446 #ifndef macintosh
1447 /* Called before init_window_once for Mac OS. */
1448 syms_of_search ();
1449 syms_of_frame ();
1450 #endif
1451 syms_of_syntax ();
1452 syms_of_term ();
1453 syms_of_undo ();
1454 #ifdef HAVE_SOUND
1455 syms_of_sound ();
1456 #endif
1457 #ifndef macintosh
1458 /* Called before init_window_once for Mac OS. */
1459 syms_of_textprop ();
1460 #endif
1461 syms_of_composite ();
1462 #ifdef VMS
1463 syms_of_vmsproc ();
1464 #endif /* VMS */
1465 #ifdef WINDOWSNT
1466 syms_of_ntproc ();
1467 #endif /* WINDOWSNT */
1468 syms_of_window ();
1469 syms_of_xdisp ();
1470 #ifdef HAVE_X_WINDOWS
1471 syms_of_xterm ();
1472 syms_of_xfns ();
1473 syms_of_fontset ();
1474 #ifdef HAVE_X11
1475 syms_of_xselect ();
1476 #endif
1477 #endif /* HAVE_X_WINDOWS */
1478
1479 #ifndef HAVE_NTGUI
1480 #ifndef macintosh
1481 syms_of_xmenu ();
1482 #endif
1483 #endif
1484
1485 #ifdef HAVE_NTGUI
1486 syms_of_w32term ();
1487 syms_of_w32fns ();
1488 syms_of_w32select ();
1489 syms_of_w32menu ();
1490 syms_of_fontset ();
1491 #endif /* HAVE_NTGUI */
1492
1493 #ifdef SYMS_SYSTEM
1494 SYMS_SYSTEM;
1495 #endif
1496
1497 #ifdef SYMS_MACHINE
1498 SYMS_MACHINE;
1499 #endif
1500
1501 keys_of_casefiddle ();
1502 keys_of_cmds ();
1503 keys_of_buffer ();
1504 keys_of_keyboard ();
1505 keys_of_keymap ();
1506 keys_of_minibuf ();
1507 keys_of_window ();
1508 }
1509
1510 if (!noninteractive)
1511 {
1512 #ifdef VMS
1513 init_vms_input ();/* init_display calls get_frame_size, that needs this. */
1514 #endif /* VMS */
1515 init_display (); /* Determine terminal type. init_sys_modes uses results. */
1516 }
1517 #ifndef macintosh
1518 /* Called before init_window_once for Mac OS. */
1519 init_keyboard (); /* This too must precede init_sys_modes. */
1520 #endif
1521 #ifdef VMS
1522 init_vmsproc (); /* And this too. */
1523 #endif /* VMS */
1524 init_sys_modes (); /* Init system terminal modes (RAW or CBREAK, etc.). */
1525 #ifdef HAVE_X_WINDOWS
1526 init_xfns ();
1527 #endif /* HAVE_X_WINDOWS */
1528 init_fns ();
1529 init_xdisp ();
1530 init_macros ();
1531 init_editfns ();
1532 init_floatfns ();
1533 #ifdef VMS
1534 init_vmsfns ();
1535 #endif /* VMS */
1536 init_process ();
1537 #ifdef HAVE_SOUND
1538 init_sound ();
1539 #endif
1540 init_window ();
1541
1542 if (!initialized)
1543 {
1544 char *file;
1545 /* Handle -l loadup, args passed by Makefile. */
1546 if (argmatch (argv, argc, "-l", "--load", 3, &file, &skip_args))
1547 Vtop_level = Fcons (intern ("load"),
1548 Fcons (build_string (file), Qnil));
1549 #ifdef CANNOT_DUMP
1550 /* Unless next switch is -nl, load "loadup.el" first thing. */
1551 if (! no_loadup)
1552 Vtop_level = Fcons (intern ("load"),
1553 Fcons (build_string ("loadup.el"), Qnil));
1554 #endif /* CANNOT_DUMP */
1555 }
1556
1557 if (initialized)
1558 {
1559 #ifdef HAVE_TZSET
1560 {
1561 /* If the execution TZ happens to be the same as the dump TZ,
1562 change it to some other value and then change it back,
1563 to force the underlying implementation to reload the TZ info.
1564 This is needed on implementations that load TZ info from files,
1565 since the TZ file contents may differ between dump and execution. */
1566 char *tz = getenv ("TZ");
1567 if (tz && !strcmp (tz, dump_tz))
1568 {
1569 ++*tz;
1570 tzset ();
1571 --*tz;
1572 }
1573 }
1574 #endif
1575 }
1576
1577 /* Set up for profiling. This is known to work on FreeBSD and
1578 GNU/Linux. It might work on some other systems too. Give it a
1579 try and tell us if it works on your system. To compile for
1580 profiling use something like `make CFLAGS="-pg -g -O -DPROFILING=1'. */
1581 #if defined (__FreeBSD__) || defined (__linux)
1582 #ifdef PROFILING
1583 if (initialized)
1584 {
1585 extern void _mcleanup ();
1586 extern char etext;
1587 extern void safe_bcopy ();
1588 extern void dump_opcode_frequencies ();
1589
1590 atexit (_mcleanup);
1591 /* This uses safe_bcopy because that function comes first in the
1592 Emacs executable. It might be better to use something that
1593 gives the start of the text segment, but start_of_text is not
1594 defined on all systems now. */
1595 monstartup (safe_bcopy, &etext);
1596 }
1597 else
1598 moncontrol (0);
1599 #endif
1600 #endif
1601
1602 initialized = 1;
1603
1604 #ifdef LOCALTIME_CACHE
1605 /* Some versions of localtime have a bug. They cache the value of the time
1606 zone rather than looking it up every time. Since localtime() is
1607 called to bolt the undumping time into the undumped emacs, this
1608 results in localtime ignoring the TZ environment variable.
1609 This flushes the new TZ value into localtime. */
1610 tzset ();
1611 #endif /* defined (LOCALTIME_CACHE) */
1612
1613 /* Enter editor command loop. This never returns. */
1614 Frecursive_edit ();
1615 /* NOTREACHED */
1616 return 0;
1617 }
1618 \f
1619 /* Sort the args so we can find the most important ones
1620 at the beginning of argv. */
1621
1622 /* First, here's a table of all the standard options. */
1623
1624 struct standard_args
1625 {
1626 char *name;
1627 char *longname;
1628 int priority;
1629 int nargs;
1630 };
1631
1632 struct standard_args standard_args[] =
1633 {
1634 { "-version", "--version", 150, 0 },
1635 #ifdef HAVE_SHM
1636 { "-nl", "--no-shared-memory", 140, 0 },
1637 #endif
1638 #ifdef VMS
1639 { "-map", "--map-data", 130, 0 },
1640 #endif
1641 { "-t", "--terminal", 120, 1 },
1642 { "-nw", "--no-window-system", 110, 0 },
1643 { "-nw", "--no-windows", 110, 0 },
1644 { "-batch", "--batch", 100, 0 },
1645 { "-help", "--help", 90, 0 },
1646 { "-no-unibyte", "--no-unibyte", 83, 0 },
1647 { "-multibyte", "--multibyte", 82, 0 },
1648 { "-unibyte", "--unibyte", 81, 0 },
1649 { "-no-multibyte", "--no-multibyte", 80, 0 },
1650 #ifdef CANNOT_DUMP
1651 { "-nl", "--no-loadup", 70, 0 },
1652 #endif
1653 /* -d must come last before the options handled in startup.el. */
1654 { "-d", "--display", 60, 1 },
1655 { "-display", 0, 60, 1 },
1656 /* Now for the options handled in startup.el. */
1657 { "-q", "--no-init-file", 50, 0 },
1658 { "-no-init-file", 0, 50, 0 },
1659 { "-no-site-file", "--no-site-file", 40, 0 },
1660 { "-u", "--user", 30, 1 },
1661 { "-user", 0, 30, 1 },
1662 { "-debug-init", "--debug-init", 20, 0 },
1663 { "-i", "--icon-type", 15, 0 },
1664 { "-itype", 0, 15, 0 },
1665 { "-iconic", "--iconic", 15, 0 },
1666 { "-bg", "--background-color", 10, 1 },
1667 { "-background", 0, 10, 1 },
1668 { "-fg", "--foreground-color", 10, 1 },
1669 { "-foreground", 0, 10, 1 },
1670 { "-bd", "--border-color", 10, 1 },
1671 { "-bw", "--border-width", 10, 1 },
1672 { "-ib", "--internal-border", 10, 1 },
1673 { "-ms", "--mouse-color", 10, 1 },
1674 { "-cr", "--cursor-color", 10, 1 },
1675 { "-fn", "--font", 10, 1 },
1676 { "-font", 0, 10, 1 },
1677 { "-fs", "--fullscreen", 10, 0 },
1678 { "-fw", "--fullwidth", 10, 0 },
1679 { "-fh", "--fullheight", 10, 0 },
1680 { "-g", "--geometry", 10, 1 },
1681 { "-geometry", 0, 10, 1 },
1682 { "-T", "--title", 10, 1 },
1683 { "-title", 0, 10, 1 },
1684 { "-name", "--name", 10, 1 },
1685 { "-xrm", "--xrm", 10, 1 },
1686 { "-r", "--reverse-video", 5, 0 },
1687 { "-rv", 0, 5, 0 },
1688 { "-reverse", 0, 5, 0 },
1689 { "-hb", "--horizontal-scroll-bars", 5, 0 },
1690 { "-vb", "--vertical-scroll-bars", 5, 0 },
1691 { "-color", "--color", 5, 0},
1692 /* These have the same priority as ordinary file name args,
1693 so they are not reordered with respect to those. */
1694 { "-L", "--directory", 0, 1 },
1695 { "-directory", 0, 0, 1 },
1696 { "-l", "--load", 0, 1 },
1697 { "-load", 0, 0, 1 },
1698 { "-f", "--funcall", 0, 1 },
1699 { "-funcall", 0, 0, 1 },
1700 { "-eval", "--eval", 0, 1 },
1701 { "-execute", "--execute", 0, 1 },
1702 { "-find-file", "--find-file", 0, 1 },
1703 { "-visit", "--visit", 0, 1 },
1704 { "-file", "--file", 0, 1 },
1705 { "-insert", "--insert", 0, 1 },
1706 /* This should be processed after ordinary file name args and the like. */
1707 { "-kill", "--kill", -10, 0 },
1708 };
1709
1710 /* Reorder the elements of ARGV (assumed to have ARGC elements)
1711 so that the highest priority ones come first.
1712 Do not change the order of elements of equal priority.
1713 If an option takes an argument, keep it and its argument together.
1714
1715 If an option that takes no argument appears more
1716 than once, eliminate all but one copy of it. */
1717
1718 static void
1719 sort_args (argc, argv)
1720 int argc;
1721 char **argv;
1722 {
1723 char **new = (char **) xmalloc (sizeof (char *) * argc);
1724 /* For each element of argv,
1725 the corresponding element of options is:
1726 0 for an option that takes no arguments,
1727 1 for an option that takes one argument, etc.
1728 -1 for an ordinary non-option argument. */
1729 int *options = (int *) xmalloc (sizeof (int) * argc);
1730 int *priority = (int *) xmalloc (sizeof (int) * argc);
1731 int to = 1;
1732 int incoming_used = 1;
1733 int from;
1734 int i;
1735
1736 /* Categorize all the options,
1737 and figure out which argv elts are option arguments. */
1738 for (from = 1; from < argc; from++)
1739 {
1740 options[from] = -1;
1741 priority[from] = 0;
1742 if (argv[from][0] == '-')
1743 {
1744 int match, thislen;
1745 char *equals;
1746
1747 /* If we have found "--", don't consider
1748 any more arguments as options. */
1749 if (argv[from][1] == '-' && argv[from][2] == 0)
1750 {
1751 /* Leave the "--", and everything following it, at the end. */
1752 for (; from < argc; from++)
1753 {
1754 priority[from] = -100;
1755 options[from] = -1;
1756 }
1757 break;
1758 }
1759
1760 /* Look for a match with a known old-fashioned option. */
1761 for (i = 0; i < sizeof (standard_args) / sizeof (standard_args[0]); i++)
1762 if (!strcmp (argv[from], standard_args[i].name))
1763 {
1764 options[from] = standard_args[i].nargs;
1765 priority[from] = standard_args[i].priority;
1766 if (from + standard_args[i].nargs >= argc)
1767 fatal ("Option `%s' requires an argument\n", argv[from]);
1768 from += standard_args[i].nargs;
1769 goto done;
1770 }
1771
1772 /* Look for a match with a known long option.
1773 MATCH is -1 if no match so far, -2 if two or more matches so far,
1774 >= 0 (the table index of the match) if just one match so far. */
1775 if (argv[from][1] == '-')
1776 {
1777 match = -1;
1778 thislen = strlen (argv[from]);
1779 equals = index (argv[from], '=');
1780 if (equals != 0)
1781 thislen = equals - argv[from];
1782
1783 for (i = 0;
1784 i < sizeof (standard_args) / sizeof (standard_args[0]); i++)
1785 if (standard_args[i].longname
1786 && !strncmp (argv[from], standard_args[i].longname,
1787 thislen))
1788 {
1789 if (match == -1)
1790 match = i;
1791 else
1792 match = -2;
1793 }
1794
1795 /* If we found exactly one match, use that. */
1796 if (match >= 0)
1797 {
1798 options[from] = standard_args[match].nargs;
1799 priority[from] = standard_args[match].priority;
1800 /* If --OPTION=VALUE syntax is used,
1801 this option uses just one argv element. */
1802 if (equals != 0)
1803 options[from] = 0;
1804 if (from + options[from] >= argc)
1805 fatal ("Option `%s' requires an argument\n", argv[from]);
1806 from += options[from];
1807 }
1808 }
1809 done: ;
1810 }
1811 }
1812
1813 /* Copy the arguments, in order of decreasing priority, to NEW. */
1814 new[0] = argv[0];
1815 while (incoming_used < argc)
1816 {
1817 int best = -1;
1818 int best_priority = -9999;
1819
1820 /* Find the highest priority remaining option.
1821 If several have equal priority, take the first of them. */
1822 for (from = 1; from < argc; from++)
1823 {
1824 if (argv[from] != 0 && priority[from] > best_priority)
1825 {
1826 best_priority = priority[from];
1827 best = from;
1828 }
1829 /* Skip option arguments--they are tied to the options. */
1830 if (options[from] > 0)
1831 from += options[from];
1832 }
1833
1834 if (best < 0)
1835 abort ();
1836
1837 /* Copy the highest priority remaining option, with its args, to NEW.
1838 Unless it is a duplicate of the previous one. */
1839 if (! (options[best] == 0
1840 && ! strcmp (new[to - 1], argv[best])))
1841 {
1842 new[to++] = argv[best];
1843 for (i = 0; i < options[best]; i++)
1844 new[to++] = argv[best + i + 1];
1845 }
1846
1847 incoming_used += 1 + (options[best] > 0 ? options[best] : 0);
1848
1849 /* Clear out this option in ARGV. */
1850 argv[best] = 0;
1851 for (i = 0; i < options[best]; i++)
1852 argv[best + i + 1] = 0;
1853 }
1854
1855 /* If duplicate options were deleted, fill up extra space with null ptrs. */
1856 while (to < argc)
1857 new[to++] = 0;
1858
1859 bcopy (new, argv, sizeof (char *) * argc);
1860
1861 free (options);
1862 free (new);
1863 free (priority);
1864 }
1865 \f
1866 DEFUN ("kill-emacs", Fkill_emacs, Skill_emacs, 0, 1, "P",
1867 doc: /* Exit the Emacs job and kill it.
1868 If ARG is an integer, return ARG as the exit program code.
1869 If ARG is a string, stuff it as keyboard input.
1870
1871 The value of `kill-emacs-hook', if not void,
1872 is a list of functions (of no args),
1873 all of which are called before Emacs is actually killed. */)
1874 (arg)
1875 Lisp_Object arg;
1876 {
1877 struct gcpro gcpro1;
1878
1879 GCPRO1 (arg);
1880
1881 if (feof (stdin))
1882 arg = Qt;
1883
1884 if (!NILP (Vrun_hooks) && !noninteractive)
1885 call1 (Vrun_hooks, intern ("kill-emacs-hook"));
1886
1887 UNGCPRO;
1888
1889 /* Is it really necessary to do this deassign
1890 when we are going to exit anyway? */
1891 /* #ifdef VMS
1892 stop_vms_input ();
1893 #endif */
1894
1895 shut_down_emacs (0, 0, STRINGP (arg) ? arg : Qnil);
1896
1897 /* If we have an auto-save list file,
1898 kill it because we are exiting Emacs deliberately (not crashing).
1899 Do it after shut_down_emacs, which does an auto-save. */
1900 if (STRINGP (Vauto_save_list_file_name))
1901 unlink (XSTRING (Vauto_save_list_file_name)->data);
1902
1903 exit (INTEGERP (arg) ? XINT (arg)
1904 #ifdef VMS
1905 : 1
1906 #else
1907 : 0
1908 #endif
1909 );
1910 /* NOTREACHED */
1911 }
1912
1913
1914 /* Perform an orderly shutdown of Emacs. Autosave any modified
1915 buffers, kill any child processes, clean up the terminal modes (if
1916 we're in the foreground), and other stuff like that. Don't perform
1917 any redisplay; this may be called when Emacs is shutting down in
1918 the background, or after its X connection has died.
1919
1920 If SIG is a signal number, print a message for it.
1921
1922 This is called by fatal signal handlers, X protocol error handlers,
1923 and Fkill_emacs. */
1924
1925 void
1926 shut_down_emacs (sig, no_x, stuff)
1927 int sig, no_x;
1928 Lisp_Object stuff;
1929 {
1930 /* Prevent running of hooks from now on. */
1931 Vrun_hooks = Qnil;
1932
1933 /* If we are controlling the terminal, reset terminal modes. */
1934 #ifdef EMACS_HAVE_TTY_PGRP
1935 {
1936 int pgrp = EMACS_GETPGRP (0);
1937
1938 int tpgrp;
1939 if (EMACS_GET_TTY_PGRP (0, &tpgrp) != -1
1940 && tpgrp == pgrp)
1941 {
1942 fflush (stdout);
1943 reset_sys_modes ();
1944 if (sig && sig != SIGTERM)
1945 fprintf (stderr, "Fatal error (%d).", sig);
1946 }
1947 }
1948 #else
1949 fflush (stdout);
1950 reset_sys_modes ();
1951 #endif
1952
1953 stuff_buffered_input (stuff);
1954
1955 kill_buffer_processes (Qnil);
1956 Fdo_auto_save (Qt, Qnil);
1957
1958 #ifdef CLASH_DETECTION
1959 unlock_all_files ();
1960 #endif
1961
1962 #ifdef VMS
1963 kill_vms_processes ();
1964 #endif
1965
1966 #if 0 /* This triggers a bug in XCloseDisplay and is not needed. */
1967 #ifdef HAVE_X_WINDOWS
1968 /* It's not safe to call intern here. Maybe we are crashing. */
1969 if (!noninteractive && SYMBOLP (Vwindow_system)
1970 && XSYMBOL (Vwindow_system)->name->size == 1
1971 && XSYMBOL (Vwindow_system)->name->data[0] == 'x'
1972 && ! no_x)
1973 Fx_close_current_connection ();
1974 #endif /* HAVE_X_WINDOWS */
1975 #endif
1976
1977 #ifdef SIGIO
1978 /* There is a tendency for a SIGIO signal to arrive within exit,
1979 and cause a SIGHUP because the input descriptor is already closed. */
1980 unrequest_sigio ();
1981 signal (SIGIO, SIG_IGN);
1982 #endif
1983
1984 #ifdef WINDOWSNT
1985 term_ntproc ();
1986 #endif
1987
1988 /* Do this only if terminating normally, we want glyph matrices
1989 etc. in a core dump. */
1990 if (sig == 0 || sig == SIGTERM)
1991 {
1992 check_glyph_memory ();
1993 check_message_stack ();
1994 }
1995
1996 #ifdef MSDOS
1997 dos_cleanup ();
1998 #endif
1999 }
2000
2001
2002 \f
2003 #ifndef CANNOT_DUMP
2004
2005 #ifdef HAVE_SHM
2006
2007 DEFUN ("dump-emacs-data", Fdump_emacs_data, Sdump_emacs_data, 1, 1, 0,
2008 doc: /* Dump current state of Emacs into data file FILENAME.
2009 This function exists on systems that use HAVE_SHM. */)
2010 (filename)
2011 Lisp_Object filename;
2012 {
2013 extern char my_edata[];
2014 Lisp_Object tem;
2015
2016 check_pure_size ();
2017 CHECK_STRING (filename);
2018 filename = Fexpand_file_name (filename, Qnil);
2019
2020 tem = Vpurify_flag;
2021 Vpurify_flag = Qnil;
2022
2023 fflush (stdout);
2024 /* Tell malloc where start of impure now is. */
2025 /* Also arrange for warnings when nearly out of space. */
2026 #ifndef SYSTEM_MALLOC
2027 memory_warnings (my_edata, malloc_warning);
2028 #endif
2029 map_out_data (XSTRING (filename)->data);
2030
2031 Vpurify_flag = tem;
2032
2033 return Qnil;
2034 }
2035
2036 #else /* not HAVE_SHM */
2037
2038 DEFUN ("dump-emacs", Fdump_emacs, Sdump_emacs, 2, 2, 0,
2039 doc: /* Dump current state of Emacs into executable file FILENAME.
2040 Take symbols from SYMFILE (presumably the file you executed to run Emacs).
2041 This is used in the file `loadup.el' when building Emacs.
2042
2043 You must run Emacs in batch mode in order to dump it. */)
2044 (filename, symfile)
2045 Lisp_Object filename, symfile;
2046 {
2047 extern char my_edata[];
2048 Lisp_Object tem;
2049 Lisp_Object symbol;
2050 int count = BINDING_STACK_SIZE ();
2051
2052 check_pure_size ();
2053
2054 if (! noninteractive)
2055 error ("Dumping Emacs works only in batch mode");
2056
2057 /* Bind `command-line-processed' to nil before dumping,
2058 so that the dumped Emacs will process its command line
2059 and set up to work with X windows if appropriate. */
2060 symbol = intern ("command-line-process");
2061 specbind (symbol, Qnil);
2062
2063 CHECK_STRING (filename);
2064 filename = Fexpand_file_name (filename, Qnil);
2065 if (!NILP (symfile))
2066 {
2067 CHECK_STRING (symfile);
2068 if (XSTRING (symfile)->size)
2069 symfile = Fexpand_file_name (symfile, Qnil);
2070 }
2071
2072 tem = Vpurify_flag;
2073 Vpurify_flag = Qnil;
2074
2075 #ifdef HAVE_TZSET
2076 set_time_zone_rule (dump_tz);
2077 #ifndef LOCALTIME_CACHE
2078 /* Force a tz reload, since set_time_zone_rule doesn't. */
2079 tzset ();
2080 #endif
2081 #endif
2082
2083 fflush (stdout);
2084 #ifdef VMS
2085 mapout_data (XSTRING (filename)->data);
2086 #else
2087 /* Tell malloc where start of impure now is. */
2088 /* Also arrange for warnings when nearly out of space. */
2089 #ifndef SYSTEM_MALLOC
2090 #ifndef WINDOWSNT
2091 /* On Windows, this was done before dumping, and that once suffices.
2092 Meanwhile, my_edata is not valid on Windows. */
2093 memory_warnings (my_edata, malloc_warning);
2094 #endif /* not WINDOWSNT */
2095 #endif
2096 #ifdef DOUG_LEA_MALLOC
2097 malloc_state_ptr = malloc_get_state ();
2098 #endif
2099
2100 #ifdef USE_MMAP_FOR_BUFFERS
2101 mmap_set_vars (0);
2102 #endif
2103 unexec (XSTRING (filename)->data,
2104 !NILP (symfile) ? XSTRING (symfile)->data : 0, my_edata, 0, 0);
2105 #ifdef USE_MMAP_FOR_BUFFERS
2106 mmap_set_vars (1);
2107 #endif
2108 #ifdef DOUG_LEA_MALLOC
2109 free (malloc_state_ptr);
2110 #endif
2111 #endif /* not VMS */
2112
2113 Vpurify_flag = tem;
2114
2115 return unbind_to (count, Qnil);
2116 }
2117
2118 #endif /* not HAVE_SHM */
2119
2120 #endif /* not CANNOT_DUMP */
2121 \f
2122 #if HAVE_SETLOCALE
2123 /* Recover from setlocale (LC_ALL, ""). */
2124 void
2125 fixup_locale ()
2126 {
2127 /* The Emacs Lisp reader needs LC_NUMERIC to be "C",
2128 so that numbers are read and printed properly for Emacs Lisp. */
2129 setlocale (LC_NUMERIC, "C");
2130 }
2131
2132 /* Set system locale CATEGORY, with previous locale *PLOCALE, to
2133 DESIRED_LOCALE. */
2134 static void
2135 synchronize_locale (category, plocale, desired_locale)
2136 int category;
2137 Lisp_Object *plocale;
2138 Lisp_Object desired_locale;
2139 {
2140 if (! EQ (*plocale, desired_locale))
2141 {
2142 *plocale = desired_locale;
2143 setlocale (category, (STRINGP (desired_locale)
2144 ? (char *)(XSTRING (desired_locale)->data)
2145 : ""));
2146 }
2147 }
2148
2149 /* Set system time locale to match Vsystem_time_locale, if possible. */
2150 void
2151 synchronize_system_time_locale ()
2152 {
2153 synchronize_locale (LC_TIME, &Vprevious_system_time_locale,
2154 Vsystem_time_locale);
2155 }
2156
2157 /* Set system messages locale to match Vsystem_messages_locale, if
2158 possible. */
2159 void
2160 synchronize_system_messages_locale ()
2161 {
2162 #ifdef LC_MESSAGES
2163 synchronize_locale (LC_MESSAGES, &Vprevious_system_messages_locale,
2164 Vsystem_messages_locale);
2165 #endif
2166 }
2167 #endif /* HAVE_SETLOCALE */
2168 \f
2169 #ifndef SEPCHAR
2170 #define SEPCHAR ':'
2171 #endif
2172
2173 Lisp_Object
2174 decode_env_path (evarname, defalt)
2175 char *evarname, *defalt;
2176 {
2177 register char *path, *p;
2178 Lisp_Object lpath, element, tem;
2179
2180 /* It's okay to use getenv here, because this function is only used
2181 to initialize variables when Emacs starts up, and isn't called
2182 after that. */
2183 if (evarname != 0)
2184 path = (char *) getenv (evarname);
2185 else
2186 path = 0;
2187 if (!path)
2188 path = defalt;
2189 #ifdef DOS_NT
2190 /* Ensure values from the environment use the proper directory separator. */
2191 if (path)
2192 {
2193 p = alloca (strlen (path) + 1);
2194 strcpy (p, path);
2195 path = p;
2196
2197 if ('/' == DIRECTORY_SEP)
2198 dostounix_filename (path);
2199 else
2200 unixtodos_filename (path);
2201 }
2202 #endif
2203 lpath = Qnil;
2204 while (1)
2205 {
2206 p = index (path, SEPCHAR);
2207 if (!p) p = path + strlen (path);
2208 element = (p - path ? make_string (path, p - path)
2209 : build_string ("."));
2210
2211 /* Add /: to the front of the name
2212 if it would otherwise be treated as magic. */
2213 tem = Ffind_file_name_handler (element, Qt);
2214 if (! NILP (tem))
2215 element = concat2 (build_string ("/:"), element);
2216
2217 lpath = Fcons (element, lpath);
2218 if (*p)
2219 path = p + 1;
2220 else
2221 break;
2222 }
2223 return Fnreverse (lpath);
2224 }
2225
2226 void
2227 syms_of_emacs ()
2228 {
2229 Qfile_name_handler_alist = intern ("file-name-handler-alist");
2230 staticpro (&Qfile_name_handler_alist);
2231
2232 #ifndef CANNOT_DUMP
2233 #ifdef HAVE_SHM
2234 defsubr (&Sdump_emacs_data);
2235 #else
2236 defsubr (&Sdump_emacs);
2237 #endif
2238 #endif
2239
2240 defsubr (&Skill_emacs);
2241
2242 defsubr (&Sinvocation_name);
2243 defsubr (&Sinvocation_directory);
2244
2245 DEFVAR_LISP ("command-line-args", &Vcommand_line_args,
2246 doc: /* Args passed by shell to Emacs, as a list of strings. */);
2247
2248 DEFVAR_LISP ("system-type", &Vsystem_type,
2249 doc: /* Value is symbol indicating type of operating system you are using. */);
2250 Vsystem_type = intern (SYSTEM_TYPE);
2251
2252 DEFVAR_LISP ("system-configuration", &Vsystem_configuration,
2253 doc: /* Value is string indicating configuration Emacs was built for.
2254 On MS-Windows, the value reflects the OS flavor and version on which
2255 Emacs is running. */);
2256 Vsystem_configuration = build_string (EMACS_CONFIGURATION);
2257
2258 DEFVAR_LISP ("system-configuration-options", &Vsystem_configuration_options,
2259 doc: /* String containing the configuration options Emacs was built with. */);
2260 Vsystem_configuration_options = build_string (EMACS_CONFIG_OPTIONS);
2261
2262 DEFVAR_BOOL ("noninteractive", &noninteractive1,
2263 doc: /* Non-nil means Emacs is running without interactive terminal. */);
2264
2265 DEFVAR_LISP ("kill-emacs-hook", &Vkill_emacs_hook,
2266 doc: /* Hook to be run whenever kill-emacs is called.
2267 Since kill-emacs may be invoked when the terminal is disconnected (or
2268 in other similar situations), functions placed on this hook should not
2269 expect to be able to interact with the user. To ask for confirmation,
2270 see `kill-emacs-query-functions' instead. */);
2271 Vkill_emacs_hook = Qnil;
2272
2273 empty_string = build_string ("");
2274 staticpro (&empty_string);
2275
2276 #ifdef SIGUSR1
2277 DEFVAR_LISP ("signal-USR1-hook", &Vsignal_USR1_hook,
2278 doc: /* Hook to be run whenever emacs receives a USR1 signal. */);
2279 Vsignal_USR1_hook = Qnil;
2280 #ifdef SIGUSR2
2281 DEFVAR_LISP ("signal-USR2-hook", &Vsignal_USR2_hook,
2282 doc: /* Hook to be run whenever emacs receives a USR2 signal. */);
2283 Vsignal_USR2_hook = Qnil;
2284 #endif
2285 #endif
2286
2287
2288 DEFVAR_INT ("emacs-priority", &emacs_priority,
2289 doc: /* Priority for Emacs to run at.
2290 This value is effective only if set before Emacs is dumped,
2291 and only if the Emacs executable is installed with setuid to permit
2292 it to change priority. (Emacs sets its uid back to the real uid.)
2293 Currently, you need to define SET_EMACS_PRIORITY in `config.h'
2294 before you compile Emacs, to enable the code for this feature. */);
2295 emacs_priority = 0;
2296
2297 DEFVAR_LISP ("path-separator", &Vpath_separator,
2298 doc: /* The directory separator in search paths, as a string. */);
2299 {
2300 char c = SEPCHAR;
2301 Vpath_separator = make_string (&c, 1);
2302 }
2303
2304 DEFVAR_LISP ("invocation-name", &Vinvocation_name,
2305 doc: /* The program name that was used to run Emacs.
2306 Any directory names are omitted. */);
2307
2308 DEFVAR_LISP ("invocation-directory", &Vinvocation_directory,
2309 doc: /* The directory in which the Emacs executable was found, to run it.
2310 The value is nil if that directory's name is not known. */);
2311
2312 DEFVAR_LISP ("installation-directory", &Vinstallation_directory,
2313 doc: /* A directory within which to look for the `lib-src' and `etc' directories.
2314 This is non-nil when we can't find those directories in their standard
2315 installed locations, but we can find them
2316 near where the Emacs executable was found. */);
2317 Vinstallation_directory = Qnil;
2318
2319 DEFVAR_LISP ("system-messages-locale", &Vsystem_messages_locale,
2320 doc: /* System locale for messages. */);
2321 Vsystem_messages_locale = Qnil;
2322
2323 DEFVAR_LISP ("previous-system-messages-locale",
2324 &Vprevious_system_messages_locale,
2325 doc: /* Most recently used system locale for messages. */);
2326 Vprevious_system_messages_locale = Qnil;
2327
2328 DEFVAR_LISP ("system-time-locale", &Vsystem_time_locale,
2329 doc: /* System locale for time. */);
2330 Vsystem_time_locale = Qnil;
2331
2332 DEFVAR_LISP ("previous-system-time-locale", &Vprevious_system_time_locale,
2333 doc: /* Most recently used system locale for time. */);
2334 Vprevious_system_time_locale = Qnil;
2335 }