XEmacs 21.4.10 "Military Intelligence".
[chise/xemacs-chise.git.1] / src / callproc.c
1 /* Old synchronous subprocess invocation for XEmacs.
2    Copyright (C) 1985, 86, 87, 88, 93, 94, 95 Free Software Foundation, Inc.
3
4 This file is part of XEmacs.
5
6 XEmacs is free software; you can redistribute it and/or modify it
7 under the terms of the GNU General Public License as published by the
8 Free Software Foundation; either version 2, or (at your option) any
9 later version.
10
11 XEmacs is distributed in the hope that it will be useful, but WITHOUT
12 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with XEmacs; see the file COPYING.  If not, write to
18 the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
19 Boston, MA 02111-1307, USA.  */
20
21 /* Synched up with: Mule 2.0, FSF 19.30. */
22 /* Partly sync'ed with 19.36.4 */
23
24
25 /* #### This ENTIRE file is only used in batch mode.
26
27    We only need two things to get rid of both this and ntproc.c:
28
29    -- my `stderr-proc' ws, which adds support for a separate stderr
30       in asynch. subprocesses. (it's a feature in `old-call-process-internal'.)
31    -- a noninteractive event loop that supports processes.
32 */
33
34 #include <config.h>
35 #include "lisp.h"
36
37 #include "buffer.h"
38 #include "commands.h"
39 #include "insdel.h"
40 #include "lstream.h"
41 #include "process.h"
42 #include "sysdep.h"
43 #include "window.h"
44 #ifdef FILE_CODING
45 #include "file-coding.h"
46 #endif
47
48 #include "systime.h"
49 #include "sysproc.h"
50 #include "sysfile.h" /* Always include after sysproc.h */
51 #include "syssignal.h" /* Always include before systty.h */
52 #include "systty.h"
53
54 #ifdef WIN32_NATIVE
55 #define _P_NOWAIT 1     /* from process.h */
56 #include "nt.h"
57 #endif
58
59 #ifdef WIN32_NATIVE
60 /* When we are starting external processes we need to know whether they
61    take binary input (no conversion) or text input (\n is converted to
62    \r\n).  Similarly for output: if newlines are written as \r\n then it's
63    text process output, otherwise it's binary.  */
64 Lisp_Object Vbinary_process_input;
65 Lisp_Object Vbinary_process_output;
66 #endif /* WIN32_NATIVE */
67
68 Lisp_Object Vshell_file_name;
69
70 /* The environment to pass to all subprocesses when they are started.
71    This is in the semi-bogus format of ("VAR=VAL" "VAR2=VAL2" ... )
72  */
73 Lisp_Object Vprocess_environment;
74
75 /* True iff we are about to fork off a synchronous process or if we
76    are waiting for it.  */
77 volatile int synch_process_alive;
78
79 /* Nonzero => this is a string explaining death of synchronous subprocess.  */
80 const char *synch_process_death;
81
82 /* If synch_process_death is zero,
83    this is exit code of synchronous subprocess.  */
84 int synch_process_retcode;
85 \f
86 /* Clean up when exiting Fcall_process_internal.
87    On Windows, delete the temporary file on any kind of termination.
88    On Unix, kill the process and any children on termination by signal.  */
89
90 /* Nonzero if this is termination due to exit.  */
91 static int call_process_exited;
92
93 Lisp_Object Vlisp_EXEC_SUFFIXES;
94
95 static Lisp_Object
96 call_process_kill (Lisp_Object fdpid)
97 {
98   Lisp_Object fd = Fcar (fdpid);
99   Lisp_Object pid = Fcdr (fdpid);
100
101   if (!NILP (fd))
102     close (XINT (fd));
103
104   if (!NILP (pid))
105     EMACS_KILLPG (XINT (pid), SIGKILL);
106
107   synch_process_alive = 0;
108   return Qnil;
109 }
110
111 static Lisp_Object
112 call_process_cleanup (Lisp_Object fdpid)
113 {
114   int fd  = XINT (Fcar (fdpid));
115   int pid = XINT (Fcdr (fdpid));
116
117   if (!call_process_exited &&
118       EMACS_KILLPG (pid, SIGINT) == 0)
119   {
120     int speccount = specpdl_depth ();
121
122     record_unwind_protect (call_process_kill, fdpid);
123     /* #### "c-G" -- need non-consing Single-key-description */
124     message ("Waiting for process to die...(type C-g again to kill it instantly)");
125
126 #ifdef WIN32_NATIVE
127     {
128       HANDLE pHandle = OpenProcess (PROCESS_ALL_ACCESS, 0, pid);
129       if (pHandle == NULL)
130         warn_when_safe (Qprocess, Qwarning,
131                         "cannot open process (PID %d) for cleanup", pid);
132       else
133         wait_for_termination (pHandle);
134     }
135 #else
136     wait_for_termination (pid);
137 #endif
138
139     /* "Discard" the unwind protect.  */
140     XCAR (fdpid) = Qnil;
141     XCDR (fdpid) = Qnil;
142     unbind_to (speccount, Qnil);
143
144     message ("Waiting for process to die... done");
145   }
146   synch_process_alive = 0;
147   close (fd);
148   return Qnil;
149 }
150
151 static Lisp_Object fork_error;
152 #if 0 /* UNUSED */
153 static void
154 report_fork_error (char *string, Lisp_Object data)
155 {
156   Lisp_Object errstring = lisp_strerror (errno);
157
158   fork_error = Fcons (build_string (string), Fcons (errstring, data));
159
160   /* terminate this branch of the fork, without closing stdin/out/etc. */
161   _exit (1);
162 }
163 #endif /* unused */
164
165 DEFUN ("old-call-process-internal", Fold_call_process_internal, 1, MANY, 0, /*
166 Call PROGRAM synchronously in separate process, with coding-system specified.
167 Arguments are
168  (PROGRAM &optional INFILE BUFFER DISPLAY &rest ARGS).
169 The program's input comes from file INFILE (nil means `/dev/null').
170 Insert output in BUFFER before point; t means current buffer;
171  nil for BUFFER means discard it; 0 means discard and don't wait.
172 BUFFER can also have the form (REAL-BUFFER STDERR-FILE); in that case,
173 REAL-BUFFER says what to do with standard output, as above,
174 while STDERR-FILE says what to do with standard error in the child.
175 STDERR-FILE may be nil (discard standard error output),
176 t (mix it with ordinary output), or a file name string.
177
178 Fourth arg DISPLAY non-nil means redisplay buffer as output is inserted.
179 Remaining arguments are strings passed as command arguments to PROGRAM.
180
181 If BUFFER is 0, `call-process' returns immediately with value nil.
182 Otherwise it waits for PROGRAM to terminate and returns a numeric exit status
183  or a signal description string.
184 If you quit, the process is killed with SIGINT, or SIGKILL if you
185  quit again.
186 */
187        (int nargs, Lisp_Object *args))
188 {
189   /* This function can GC */
190   Lisp_Object infile, buffer, current_dir, display, path;
191   int fd[2];
192   int filefd;
193 #ifdef WIN32_NATIVE
194   HANDLE pHandle;
195 #endif
196   int pid;
197   char buf[16384];
198   char *bufptr = buf;
199   int bufsize = 16384;
200   int speccount = specpdl_depth ();
201   struct gcpro gcpro1, gcpro2, gcpro3;
202   char **new_argv = alloca_array (char *, max (2, nargs - 2));
203
204   /* File to use for stderr in the child.
205      t means use same as standard output.  */
206   Lisp_Object error_file;
207
208   CHECK_STRING (args[0]);
209
210   error_file = Qt;
211
212 #if defined (NO_SUBPROCESSES)
213   /* Without asynchronous processes we cannot have BUFFER == 0.  */
214   if (nargs >= 3 && !INTP (args[2]))
215     error ("Operating system cannot handle asynchronous subprocesses");
216 #endif /* NO_SUBPROCESSES */
217
218   /* Do this before building new_argv because GC in Lisp code
219    *  called by various filename-hacking routines might relocate strings */
220   locate_file (Vexec_path, args[0], Vlisp_EXEC_SUFFIXES, &path, X_OK);
221
222   /* Make sure that the child will be able to chdir to the current
223      buffer's current directory, or its unhandled equivalent.  We
224      can't just have the child check for an error when it does the
225      chdir, since it's in a vfork. */
226   {
227     struct gcpro ngcpro1, ngcpro2;
228     /* Do this test before building new_argv because GC in Lisp code
229      *  called by various filename-hacking routines might relocate strings */
230     /* Make sure that the child will be able to chdir to the current
231        buffer's current directory.  We can't just have the child check
232        for an error when it does the chdir, since it's in a vfork.  */
233
234     current_dir = current_buffer->directory;
235     NGCPRO2 (current_dir, path);   /* Caller gcprotects args[] */
236     current_dir = Funhandled_file_name_directory (current_dir);
237     current_dir = expand_and_dir_to_file (current_dir, Qnil);
238 #if 0
239     /* This is in FSF, but it breaks everything in the presence of
240        ange-ftp-visited files, so away with it.  */
241     if (NILP (Ffile_accessible_directory_p (current_dir)))
242       report_file_error ("Setting current directory",
243                          Fcons (current_buffer->directory, Qnil));
244 #endif /* 0 */
245     NUNGCPRO;
246   }
247
248   GCPRO2 (current_dir, path);
249
250   if (nargs >= 2 && ! NILP (args[1]))
251     {
252       struct gcpro ngcpro1;
253       NGCPRO1 (current_buffer->directory);
254       infile = Fexpand_file_name (args[1], current_buffer->directory);
255       NUNGCPRO;
256       CHECK_STRING (infile);
257     }
258   else
259     infile = build_string (NULL_DEVICE);
260
261   UNGCPRO;
262
263   GCPRO3 (infile, current_dir, path);   /* Fexpand_file_name might trash it */
264
265   if (nargs >= 3)
266     {
267       buffer = args[2];
268
269       /* If BUFFER is a list, its meaning is
270          (BUFFER-FOR-STDOUT FILE-FOR-STDERR).  */
271       if (CONSP (buffer))
272         {
273           if (CONSP (XCDR (buffer)))
274             {
275               Lisp_Object file_for_stderr = XCAR (XCDR (buffer));
276
277               if (NILP (file_for_stderr) || EQ (Qt, file_for_stderr))
278                 error_file = file_for_stderr;
279               else
280                 error_file = Fexpand_file_name (file_for_stderr, Qnil);
281             }
282
283           buffer = XCAR (buffer);
284         }
285
286       if (!(EQ (buffer, Qnil)
287             || EQ (buffer, Qt)
288             || ZEROP (buffer)))
289         {
290           Lisp_Object spec_buffer = buffer;
291           buffer = Fget_buffer (buffer);
292           /* Mention the buffer name for a better error message.  */
293           if (NILP (buffer))
294             CHECK_BUFFER (spec_buffer);
295           CHECK_BUFFER (buffer);
296         }
297     }
298   else
299     buffer = Qnil;
300
301   UNGCPRO;
302
303   display = ((nargs >= 4) ? args[3] : Qnil);
304
305   /* From here we assume we won't GC (unless an error is signaled). */
306   {
307     REGISTER int i;
308     for (i = 4; i < nargs; i++)
309       {
310         CHECK_STRING (args[i]);
311         new_argv[i - 3] = (char *) XSTRING_DATA (args[i]);
312       }
313   }
314   new_argv[max(nargs - 3,1)] = 0;
315
316   if (NILP (path))
317     report_file_error ("Searching for program", Fcons (args[0], Qnil));
318   new_argv[0] = (char *) XSTRING_DATA (path);
319
320   filefd = open ((char *) XSTRING_DATA (infile), O_RDONLY | OPEN_BINARY, 0);
321   if (filefd < 0)
322     report_file_error ("Opening process input file", Fcons (infile, Qnil));
323
324   if (INTP (buffer))
325     {
326       fd[1] = open (NULL_DEVICE, O_WRONLY | OPEN_BINARY, 0);
327       fd[0] = -1;
328     }
329   else
330     {
331       pipe (fd);
332 #if 0
333       /* Replaced by close_process_descs */
334       set_exclusive_use (fd[0]);
335 #endif
336     }
337
338   {
339     /* child_setup must clobber environ in systems with true vfork.
340        Protect it from permanent change.  */
341     REGISTER char **save_environ = environ;
342     REGISTER int fd1 = fd[1];
343     int fd_error = fd1;
344
345     /* Record that we're about to create a synchronous process.  */
346     synch_process_alive = 1;
347
348     /* These vars record information from process termination.
349        Clear them now before process can possibly terminate,
350        to avoid timing error if process terminates soon.  */
351     synch_process_death = 0;
352     synch_process_retcode = 0;
353
354     if (NILP (error_file))
355       fd_error = open (NULL_DEVICE, O_WRONLY | OPEN_BINARY);
356     else if (STRINGP (error_file))
357       {
358         fd_error = open ((const char *) XSTRING_DATA (error_file),
359 #ifdef WIN32_NATIVE
360                          O_WRONLY | O_TRUNC | O_CREAT | O_TEXT,
361                          S_IREAD | S_IWRITE
362 #else  /* not WIN32_NATIVE */
363                          O_WRONLY | O_TRUNC | O_CREAT | OPEN_BINARY,
364                          CREAT_MODE
365 #endif /* not WIN32_NATIVE */
366                          );
367       }
368
369     if (fd_error < 0)
370       {
371         int save_errno = errno;
372         close (filefd);
373         close (fd[0]);
374         if (fd1 >= 0)
375           close (fd1);
376         errno = save_errno;
377         report_file_error ("Cannot open", Fcons(error_file, Qnil));
378       }
379
380     fork_error = Qnil;
381 #ifdef WIN32_NATIVE
382     pid = child_setup (filefd, fd1, fd_error, new_argv,
383                        (char *) XSTRING_DATA (current_dir));
384     if (!INTP (buffer))
385       {
386         /* OpenProcess() as soon after child_setup as possible.  It's too
387            late once the process terminated. */
388         pHandle = OpenProcess(PROCESS_ALL_ACCESS, 0, pid);
389 #if 0
390         if (pHandle == NULL)
391           {
392             /* #### seems to cause crash in unbind_to(...) below. APA */
393             warn_when_safe (Qprocess, Qwarning,
394                             "cannot open process to wait for");
395           }
396 #endif
397       }
398     /* Close STDERR into the parent process.  We no longer need it. */
399     if (fd_error >= 0)
400       close (fd_error);
401 #else  /* not WIN32_NATIVE */
402     pid = fork ();
403
404     if (pid == 0)
405       {
406         if (fd[0] >= 0)
407           close (fd[0]);
408         /* This is necessary because some shells may attempt to
409            access the current controlling terminal and will hang
410            if they are run in the background, as will be the case
411            when XEmacs is started in the background.  Martin
412            Buchholz observed this problem running a subprocess
413            that used zsh to call gzip to uncompress an info
414            file. */
415         disconnect_controlling_terminal ();
416         child_setup (filefd, fd1, fd_error, new_argv,
417                      (char *) XSTRING_DATA (current_dir));
418       }
419     if (fd_error >= 0)
420       close (fd_error);
421
422 #endif /* not WIN32_NATIVE */
423
424     environ = save_environ;
425
426     /* Close most of our fd's, but not fd[0]
427        since we will use that to read input from.  */
428     close (filefd);
429     if (fd1 >= 0)
430       close (fd1);
431   }
432
433   if (!NILP (fork_error))
434     signal_error (Qfile_error, fork_error);
435
436 #ifndef WIN32_NATIVE
437   if (pid < 0)
438     {
439       int save_errno = errno;
440       if (fd[0] >= 0)
441         close (fd[0]);
442       errno = save_errno;
443       report_file_error ("Doing fork", Qnil);
444     }
445 #endif
446
447   if (INTP (buffer))
448     {
449       if (fd[0] >= 0)
450         close (fd[0]);
451 #if defined (NO_SUBPROCESSES)
452       /* If Emacs has been built with asynchronous subprocess support,
453          we don't need to do this, I think because it will then have
454          the facilities for handling SIGCHLD.  */
455       wait_without_blocking ();
456 #endif /* NO_SUBPROCESSES */
457       return Qnil;
458     }
459
460   {
461     int nread;
462     int total_read = 0;
463     Lisp_Object instream;
464     struct gcpro ngcpro1;
465
466     /* Enable sending signal if user quits below.  */
467     call_process_exited = 0;
468
469     record_unwind_protect (call_process_cleanup,
470                            Fcons (make_int (fd[0]), make_int (pid)));
471
472     /* FSFmacs calls Fset_buffer() here.  We don't have to because
473        we can insert into buffers other than the current one. */
474     if (EQ (buffer, Qt))
475       XSETBUFFER (buffer, current_buffer);
476     instream = make_filedesc_input_stream (fd[0], 0, -1, LSTR_ALLOW_QUIT);
477 #ifdef FILE_CODING
478     instream =
479       make_decoding_input_stream
480         (XLSTREAM (instream),
481          Fget_coding_system (Vcoding_system_for_read));
482     Lstream_set_character_mode (XLSTREAM (instream));
483 #endif
484     NGCPRO1 (instream);
485     while (1)
486       {
487         QUIT;
488         /* Repeatedly read until we've filled as much as possible
489            of the buffer size we have.  But don't read
490            less than 1024--save that for the next bufferfull.  */
491
492         nread = 0;
493         while (nread < bufsize - 1024)
494           {
495             Lstream_data_count this_read
496               = Lstream_read (XLSTREAM (instream), bufptr + nread,
497                               bufsize - nread);
498
499             if (this_read < 0)
500               goto give_up;
501
502             if (this_read == 0)
503               goto give_up_1;
504
505             nread += this_read;
506           }
507
508       give_up_1:
509
510         /* Now NREAD is the total amount of data in the buffer.  */
511         if (nread == 0)
512           break;
513
514 #if 0
515 #ifdef WIN32_NATIVE
516        /* Until we pull out of MULE things like
517           make_decoding_input_stream(), we do the following which is
518           less elegant. --marcpa */
519         /* We did. -- kkm */
520        {
521          int lf_count = 0;
522          if (NILP (Vbinary_process_output)) {
523            nread = crlf_to_lf(nread, bufptr, &lf_count);
524          }
525        }
526 #endif
527 #endif
528
529         total_read += nread;
530
531         if (!NILP (buffer))
532           buffer_insert_raw_string (XBUFFER (buffer), (Bufbyte *) bufptr,
533                                     nread);
534
535         /* Make the buffer bigger as we continue to read more data,
536            but not past 64k.  */
537         if (bufsize < 64 * 1024 && total_read > 32 * bufsize)
538           {
539             bufsize *= 2;
540             bufptr = (char *) alloca (bufsize);
541           }
542
543         if (!NILP (display) && INTERACTIVE)
544           {
545             redisplay ();
546           }
547       }
548   give_up:
549     Lstream_close (XLSTREAM (instream));
550     NUNGCPRO;
551
552     QUIT;
553     /* Wait for it to terminate, unless it already has.  */
554 #ifdef WIN32_NATIVE
555     wait_for_termination (pHandle);
556 #else
557     wait_for_termination (pid);
558 #endif
559
560     /* Don't kill any children that the subprocess may have left behind
561        when exiting.  */
562     call_process_exited = 1;
563     unbind_to (speccount, Qnil);
564
565     if (synch_process_death)
566       return build_string (synch_process_death);
567     return make_int (synch_process_retcode);
568   }
569 }
570
571 \f
572
573 /* Move the file descriptor FD so that its number is not less than MIN. *
574    The original file descriptor remains open.  */
575 static int
576 relocate_fd (int fd, int min)
577 {
578   if (fd >= min)
579     return fd;
580   else
581     {
582       int newfd = dup (fd);
583       if (newfd == -1)
584         {
585           stderr_out ("Error while setting up child: %s\n",
586                       strerror (errno));
587           _exit (1);
588         }
589       return relocate_fd (newfd, min);
590     }
591 }
592
593 /* This is the last thing run in a newly forked inferior
594    either synchronous or asynchronous.
595    Copy descriptors IN, OUT and ERR
596    as descriptors STDIN_FILENO, STDOUT_FILENO, and STDERR_FILENO.
597    Initialize inferior's priority, pgrp, connected dir and environment.
598    then exec another program based on new_argv.
599
600    This function may change environ for the superior process.
601    Therefore, the superior process must save and restore the value
602    of environ around the fork and the call to this function.
603
604    ENV is the environment for the subprocess.
605
606    XEmacs: We've removed the SET_PGRP argument because it's already
607    done by the callers of child_setup.
608
609    CURRENT_DIR is an elisp string giving the path of the current
610    directory the subprocess should have.  Since we can't really signal
611    a decent error from within the child, this should be verified as an
612    executable directory by the parent.  */
613
614 #ifdef WIN32_NATIVE
615 int
616 #else
617 void
618 #endif
619 child_setup (int in, int out, int err, char **new_argv,
620              const char *current_dir)
621 {
622   char **env;
623   char *pwd;
624 #ifdef WIN32_NATIVE
625   int cpid;
626   HANDLE handles[4];
627 #endif /* WIN32_NATIVE */
628
629 #ifdef SET_EMACS_PRIORITY
630   if (emacs_priority != 0)
631     nice (- emacs_priority);
632 #endif
633
634   /* Under Windows, we are not in a child process at all, so we should
635      not close handles inherited from the parent -- we are the parent
636      and doing so will screw up all manner of things!  Similarly, most
637      of the rest of the cleanup done in this function is not done
638      under Windows.
639
640      #### This entire child_setup() function is an utter and complete
641      piece of shit.  I would rewrite it, at the very least splitting
642      out the Windows and non-Windows stuff into two completely
643      different functions; but instead I'm trying to make it go away
644      entirely, using the Lisp definition in process.el.  What's left
645      is to fix up the routines in event-msw.c (and in event-Xt.c and
646      event-tty.c) to allow for stream devices to be handled correctly.
647      There isn't much to do, in fact, and I'll fix it shortly.  That
648      way, the Lisp definition can be used non-interactively too. */
649 #if !defined (NO_SUBPROCESSES) && !defined (WIN32_NATIVE)
650   /* Close Emacs's descriptors that this process should not have.  */
651   close_process_descs ();
652 #endif /* not NO_SUBPROCESSES */
653 #ifndef WIN32_NATIVE
654   close_load_descs ();
655 #endif
656
657   /* Note that use of alloca is always safe here.  It's obvious for systems
658      that do not have true vfork or that have true (stack) alloca.
659      If using vfork and C_ALLOCA it is safe because that changes
660      the superior's static variables as if the superior had done alloca
661      and will be cleaned up in the usual way.  */
662   {
663     REGISTER int i;
664
665     i = strlen (current_dir);
666     pwd = alloca_array (char, i + 6);
667     memcpy (pwd, "PWD=", 4);
668     memcpy (pwd + 4, current_dir, i);
669     i += 4;
670     if (!IS_DIRECTORY_SEP (pwd[i - 1]))
671       pwd[i++] = DIRECTORY_SEP;
672     pwd[i] = 0;
673
674     /* We can't signal an Elisp error here; we're in a vfork.  Since
675        the callers check the current directory before forking, this
676        should only return an error if the directory's permissions
677        are changed between the check and this chdir, but we should
678        at least check.  */
679     if (chdir (pwd + 4) < 0)
680       {
681         /* Don't report the chdir error, or ange-ftp.el doesn't work. */
682         /* (FSFmacs does _exit (errno) here.) */
683         pwd = 0;
684       }
685     else
686       {
687         /* Strip trailing "/".  Cretinous *[]&@$#^%@#$% Un*x */
688         /* leave "//" (from FSF) */
689         while (i > 6 && IS_DIRECTORY_SEP (pwd[i - 1]))
690           pwd[--i] = 0;
691       }
692   }
693
694   /* Set `env' to a vector of the strings in Vprocess_environment.  */
695   /* + 2 to include PWD and terminating 0.  */
696   env = alloca_array (char *, XINT (Flength (Vprocess_environment)) + 2);
697   {
698     REGISTER Lisp_Object tail;
699     char **new_env = env;
700
701     /* If we have a PWD envvar and we know the real current directory,
702        pass one down, but with corrected value.  */
703     if (pwd && getenv ("PWD"))
704       *new_env++ = pwd;
705
706     /* Copy the Vprocess_environment strings into new_env.  */
707     for (tail = Vprocess_environment;
708          CONSP (tail) && STRINGP (XCAR (tail));
709          tail = XCDR (tail))
710     {
711       char **ep = env;
712       char *envvar_external;
713
714       TO_EXTERNAL_FORMAT (LISP_STRING, XCAR (tail),
715                           C_STRING_ALLOCA, envvar_external,
716                           Qfile_name);
717
718       /* See if envvar_external duplicates any string already in the env.
719          If so, don't put it in.
720          When an env var has multiple definitions,
721          we keep the definition that comes first in process-environment.  */
722       for (; ep != new_env; ep++)
723         {
724           char *p = *ep, *q = envvar_external;
725           while (1)
726             {
727               if (*q == 0)
728                 /* The string is malformed; might as well drop it.  */
729                 goto duplicate;
730               if (*q != *p)
731                 break;
732               if (*q == '=')
733                 goto duplicate;
734               p++, q++;
735             }
736         }
737       if (pwd && !strncmp ("PWD=", envvar_external, 4))
738         {
739           *new_env++ = pwd;
740           pwd = 0;
741         }
742       else
743         *new_env++ = envvar_external;
744
745     duplicate: ;
746     }
747     *new_env = 0;
748   }
749
750 #ifdef WIN32_NATIVE
751   prepare_standard_handles (in, out, err, handles);
752   set_process_dir (current_dir);
753 #else  /* not WIN32_NATIVE */
754   /* Make sure that in, out, and err are not actually already in
755      descriptors zero, one, or two; this could happen if Emacs is
756      started with its standard in, out, or error closed, as might
757      happen under X.  */
758   in  = relocate_fd (in,  3);
759   out = relocate_fd (out, 3);
760   err = relocate_fd (err, 3);
761
762   /* Set the standard input/output channels of the new process.  */
763   close (STDIN_FILENO);
764   close (STDOUT_FILENO);
765   close (STDERR_FILENO);
766
767   dup2 (in,  STDIN_FILENO);
768   dup2 (out, STDOUT_FILENO);
769   dup2 (err, STDERR_FILENO);
770
771   close (in);
772   close (out);
773   close (err);
774
775   /* Close non-process-related file descriptors. It would be cleaner to
776      close just the ones that need to be, but the following brute
777      force approach is certainly effective, and not too slow. */
778
779   {
780     int fd;
781
782     for (fd = 3; fd < MAXDESC; fd++)
783       close (fd);
784   }
785 #endif /* not WIN32_NATIVE */
786
787 #ifdef vipc
788   something missing here;
789 #endif /* vipc */
790
791 #ifdef WIN32_NATIVE
792   /* Spawn the child.  (See ntproc.c:Spawnve).  */
793   cpid = spawnve (_P_NOWAIT, new_argv[0], (const char* const*)new_argv,
794                   (const char* const*)env);
795   if (cpid == -1)
796     /* An error occurred while trying to spawn the process.  */
797     report_file_error ("Spawning child process", Qnil);
798   reset_standard_handles (in, out, err, handles);
799   return cpid;
800 #else /* not WIN32_NATIVE */
801   /* execvp does not accept an environment arg so the only way
802      to pass this environment is to set environ.  Our caller
803      is responsible for restoring the ambient value of environ.  */
804   environ = env;
805   execvp (new_argv[0], new_argv);
806
807   stdout_out ("Can't exec program %s\n", new_argv[0]);
808   _exit (1);
809 #endif /* not WIN32_NATIVE */
810 }
811
812 static int
813 getenv_internal (const Bufbyte *var,
814                  Bytecount varlen,
815                  Bufbyte **value,
816                  Bytecount *valuelen)
817 {
818   Lisp_Object scan;
819
820   for (scan = Vprocess_environment; CONSP (scan); scan = XCDR (scan))
821     {
822       Lisp_Object entry = XCAR (scan);
823
824       if (STRINGP (entry)
825           && XSTRING_LENGTH (entry) > varlen
826           && XSTRING_BYTE (entry, varlen) == '='
827 #ifdef WIN32_NATIVE
828           /* NT environment variables are case insensitive.  */
829           && ! memicmp (XSTRING_DATA (entry), var, varlen)
830 #else  /* not WIN32_NATIVE */
831           && ! memcmp (XSTRING_DATA (entry), var, varlen)
832 #endif /* not WIN32_NATIVE */
833           )
834         {
835           *value    = XSTRING_DATA   (entry) + (varlen + 1);
836           *valuelen = XSTRING_LENGTH (entry) - (varlen + 1);
837           return 1;
838         }
839     }
840
841   return 0;
842 }
843
844 DEFUN ("getenv", Fgetenv, 1, 2, "sEnvironment variable: \np", /*
845 Return the value of environment variable VAR, as a string.
846 VAR is a string, the name of the variable.
847 When invoked interactively, prints the value in the echo area.
848 */
849        (var, interactivep))
850 {
851   Bufbyte *value;
852   Bytecount valuelen;
853   Lisp_Object v = Qnil;
854   struct gcpro gcpro1;
855
856   CHECK_STRING (var);
857   GCPRO1 (v);
858   if (getenv_internal (XSTRING_DATA (var), XSTRING_LENGTH (var),
859                        &value, &valuelen))
860     v = make_string (value, valuelen);
861   if (!NILP (interactivep))
862     {
863       if (NILP (v))
864         message ("%s not defined in environment", XSTRING_DATA (var));
865       else
866         /* #### Should use Fprin1_to_string or Fprin1 to handle string
867            containing quotes correctly.  */
868         message ("\"%s\"", value);
869     }
870   RETURN_UNGCPRO (v);
871 }
872
873 /* A version of getenv that consults process_environment, easily
874    callable from C.  */
875 char *
876 egetenv (const char *var)
877 {
878   /* This cannot GC -- 7-28-00 ben */
879   Bufbyte *value;
880   Bytecount valuelen;
881
882   if (getenv_internal ((const Bufbyte *) var, strlen (var), &value, &valuelen))
883     return (char *) value;
884   else
885     return 0;
886 }
887
888 \f
889 void
890 init_callproc (void)
891 {
892   /* This function can GC */
893
894   {
895     /* jwz: always initialize Vprocess_environment, so that egetenv()
896        works in temacs. */
897     char **envp;
898     Vprocess_environment = Qnil;
899     for (envp = environ; envp && *envp; envp++)
900       Vprocess_environment =
901         Fcons (build_ext_string (*envp, Qfile_name), Vprocess_environment);
902   }
903
904   {
905     /* Initialize shell-file-name from environment variables or best guess. */
906 #ifdef WIN32_NATIVE
907     const char *shell = egetenv ("SHELL");
908     if (!shell) shell = egetenv ("COMSPEC");
909     /* Should never happen! */
910     if (!shell) shell = (GetVersion () & 0x80000000 ? "command" : "cmd");
911 #else /* not WIN32_NATIVE */
912     const char *shell = egetenv ("SHELL");
913     if (!shell) shell = "/bin/sh";
914 #endif
915
916 #if 0 /* defined (WIN32_NATIVE) */
917     /* BAD BAD BAD.  We do not wanting to be passing an XEmacs-created
918        SHELL var down to some inferior Cygwin process, which might get
919        screwed up.
920          
921        There are a few broken apps (eterm/term.el, eterm/tshell.el,
922        os-utils/terminal.el, texinfo/tex-mode.el) where this will
923        cause problems.  Those broken apps don't look at
924        shell-file-name, instead just at explicit-shell-file-name,
925        ESHELL and SHELL.  They are apparently attempting to borrow
926        what `M-x shell' uses, but that latter also looks at
927        shell-file-name.  What we want is for all of these apps to look
928        at shell-file-name, so that the user can change the value of
929        shell-file-name and everything will work out hunky-dorey.
930        */
931     
932     if (!egetenv ("SHELL"))
933       {
934         CBufbyte *faux_var = alloca_array (CBufbyte, 7 + strlen (shell));
935         sprintf (faux_var, "SHELL=%s", shell);
936         Vprocess_environment = Fcons (build_string (faux_var),
937                                       Vprocess_environment);
938       }
939 #endif /* 0 */
940
941     Vshell_file_name = build_string (shell);
942   }
943 }
944
945 #if 0
946 void
947 set_process_environment (void)
948 {
949   REGISTER char **envp;
950
951   Vprocess_environment = Qnil;
952 #ifndef CANNOT_DUMP
953   if (initialized)
954 #endif
955     for (envp = environ; *envp; envp++)
956       Vprocess_environment = Fcons (build_string (*envp),
957                                     Vprocess_environment);
958 }
959 #endif /* unused */
960
961 void
962 syms_of_callproc (void)
963 {
964   DEFSUBR (Fold_call_process_internal);
965   DEFSUBR (Fgetenv);
966 }
967
968 void
969 vars_of_callproc (void)
970 {
971   /* This function can GC */
972 #ifdef WIN32_NATIVE
973   DEFVAR_LISP ("binary-process-input", &Vbinary_process_input /*
974 *If non-nil then new subprocesses are assumed to take binary input.
975 */ );
976   Vbinary_process_input = Qnil;
977
978   DEFVAR_LISP ("binary-process-output", &Vbinary_process_output /*
979 *If non-nil then new subprocesses are assumed to produce binary output.
980 */ );
981   Vbinary_process_output = Qnil;
982 #endif /* WIN32_NATIVE */
983
984   DEFVAR_LISP ("shell-file-name", &Vshell_file_name /*
985 *File name to load inferior shells from.
986 Initialized from the SHELL environment variable.
987 */ );
988
989   DEFVAR_LISP ("process-environment", &Vprocess_environment /*
990 List of environment variables for subprocesses to inherit.
991 Each element should be a string of the form ENVVARNAME=VALUE.
992 The environment which Emacs inherits is placed in this variable
993 when Emacs starts.
994 */ );
995
996   Vlisp_EXEC_SUFFIXES = build_string (EXEC_SUFFIXES);
997   staticpro (&Vlisp_EXEC_SUFFIXES);
998 }