1/* redir.c -- Functions to perform input and output redirection. */
2
3/* Copyright (C) 1997-2005 Free Software Foundation, Inc.
4
5   This file is part of GNU Bash, the Bourne Again SHell.
6
7   Bash is free software; you can redistribute it and/or modify it
8   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   Bash is distributed in the hope that it will be useful, but WITHOUT
13   ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
14   or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
15   License for more details.
16
17   You should have received a copy of the GNU General Public License
18   along with Bash; see the file COPYING.  If not, write to the Free
19   Software Foundation, 59 Temple Place, Suite 330, Boston, MA 02111 USA. */
20#include "config.h"
21
22#if !defined (__GNUC__) && !defined (HAVE_ALLOCA_H) && defined (_AIX)
23  #pragma alloca
24#endif /* _AIX && RISC6000 && !__GNUC__ */
25
26#include <stdio.h>
27#include "bashtypes.h"
28#if !defined (_MINIX) && defined (HAVE_SYS_FILE_H)
29#  include <sys/file.h>
30#endif
31#include "filecntl.h"
32#include "posixstat.h"
33
34#if defined (HAVE_UNISTD_H)
35#  include <unistd.h>
36#endif
37
38#include <errno.h>
39
40#if !defined (errno)
41extern int errno;
42#endif
43
44#include "bashansi.h"
45#include "bashintl.h"
46
47#include "memalloc.h"
48#include "shell.h"
49#include "flags.h"
50#include "execute_cmd.h"
51#include "redir.h"
52
53#if defined (BUFFERED_INPUT)
54#  include "input.h"
55#endif
56
57int expanding_redir;
58
59extern int posixly_correct;
60extern REDIRECT *redirection_undo_list;
61extern REDIRECT *exec_redirection_undo_list;
62
63/* Static functions defined and used in this file. */
64static void add_undo_close_redirect __P((int));
65static void add_exec_redirect __P((REDIRECT *));
66static int add_undo_redirect __P((int, enum r_instruction));
67static int expandable_redirection_filename __P((REDIRECT *));
68static int stdin_redirection __P((enum r_instruction, int));
69static int do_redirection_internal __P((REDIRECT *, int));
70
71static int write_here_document __P((int, WORD_DESC *));
72static int write_here_string __P((int, WORD_DESC *));
73static int here_document_to_fd __P((WORD_DESC *, enum r_instruction));
74
75static int redir_special_open __P((int, char *, int, int, enum r_instruction));
76static int noclobber_open __P((char *, int, int, enum r_instruction));
77static int redir_open __P((char *, int, int, enum r_instruction));
78
79/* Spare redirector used when translating [N]>&WORD[-] or [N]<&WORD[-] to
80   a new redirection and when creating the redirection undo list. */
81static REDIRECTEE rd;
82
83/* Set to errno when a here document cannot be created for some reason.
84   Used to print a reasonable error message. */
85static int heredoc_errno;
86
87void
88redirection_error (temp, error)
89     REDIRECT *temp;
90     int error;
91{
92  char *filename, *allocname;
93  int oflags;
94
95  allocname = 0;
96  if (temp->redirector < 0)
97    /* This can happen when read_token_word encounters overflow, like in
98       exec 4294967297>x */
99    filename = _("file descriptor out of range");
100#ifdef EBADF
101  else if (temp->redirector >= 0 && errno == EBADF)
102    {
103      /* If we're dealing with two file descriptors, we have to guess about
104         which one is invalid; in the cases of r_{duplicating,move}_input and
105         r_{duplicating,move}_output we're here because dup2() failed. */
106      switch (temp->instruction)
107        {
108        case r_duplicating_input:
109        case r_duplicating_output:
110        case r_move_input:
111        case r_move_output:
112	  filename = allocname = itos (temp->redirectee.dest);
113	  break;
114	default:
115	  filename = allocname = itos (temp->redirector);
116	  break;
117        }
118    }
119#endif
120  else if (expandable_redirection_filename (temp))
121    {
122      if (posixly_correct && interactive_shell == 0)
123	{
124	  oflags = temp->redirectee.filename->flags;
125	  temp->redirectee.filename->flags |= W_NOGLOB;
126	}
127      filename = allocname = redirection_expand (temp->redirectee.filename);
128      if (posixly_correct && interactive_shell == 0)
129	temp->redirectee.filename->flags = oflags;
130      if (filename == 0)
131	filename = temp->redirectee.filename->word;
132    }
133  else if (temp->redirectee.dest < 0)
134    filename = "file descriptor out of range";
135  else
136    filename = allocname = itos (temp->redirectee.dest);
137
138  switch (error)
139    {
140    case AMBIGUOUS_REDIRECT:
141      internal_error (_("%s: ambiguous redirect"), filename);
142      break;
143
144    case NOCLOBBER_REDIRECT:
145      internal_error (_("%s: cannot overwrite existing file"), filename);
146      break;
147
148#if defined (RESTRICTED_SHELL)
149    case RESTRICTED_REDIRECT:
150      internal_error (_("%s: restricted: cannot redirect output"), filename);
151      break;
152#endif /* RESTRICTED_SHELL */
153
154    case HEREDOC_REDIRECT:
155      internal_error (_("cannot create temp file for here document: %s"), strerror (heredoc_errno));
156      break;
157
158    default:
159      internal_error ("%s: %s", filename, strerror (error));
160      break;
161    }
162
163  FREE (allocname);
164}
165
166/* Perform the redirections on LIST.  If flags & RX_ACTIVE, then actually
167   make input and output file descriptors, otherwise just do whatever is
168   neccessary for side effecting.  flags & RX_UNDOABLE says to remember
169   how to undo the redirections later, if non-zero.  If flags & RX_CLEXEC
170   is non-zero, file descriptors opened in do_redirection () have their
171   close-on-exec flag set. */
172int
173do_redirections (list, flags)
174     REDIRECT *list;
175     int flags;
176{
177  int error;
178  REDIRECT *temp;
179
180  if (flags & RX_UNDOABLE)
181    {
182      if (redirection_undo_list)
183	{
184	  dispose_redirects (redirection_undo_list);
185	  redirection_undo_list = (REDIRECT *)NULL;
186	}
187      if (exec_redirection_undo_list)
188	dispose_exec_redirects ();
189    }
190
191  for (temp = list; temp; temp = temp->next)
192    {
193      error = do_redirection_internal (temp, flags);
194      if (error)
195	{
196	  redirection_error (temp, error);
197	  return (error);
198	}
199    }
200  return (0);
201}
202
203/* Return non-zero if the redirection pointed to by REDIRECT has a
204   redirectee.filename that can be expanded. */
205static int
206expandable_redirection_filename (redirect)
207     REDIRECT *redirect;
208{
209  switch (redirect->instruction)
210    {
211    case r_output_direction:
212    case r_appending_to:
213    case r_input_direction:
214    case r_inputa_direction:
215    case r_err_and_out:
216    case r_input_output:
217    case r_output_force:
218    case r_duplicating_input_word:
219    case r_duplicating_output_word:
220    case r_move_input_word:
221    case r_move_output_word:
222      return 1;
223
224    default:
225      return 0;
226    }
227}
228
229/* Expand the word in WORD returning a string.  If WORD expands to
230   multiple words (or no words), then return NULL. */
231char *
232redirection_expand (word)
233     WORD_DESC *word;
234{
235  char *result;
236  WORD_LIST *tlist1, *tlist2;
237  WORD_DESC *w;
238
239  w = copy_word (word);
240  if (posixly_correct)
241    w->flags |= W_NOSPLIT;
242
243  tlist1 = make_word_list (w, (WORD_LIST *)NULL);
244  expanding_redir = 1;
245  tlist2 = expand_words_no_vars (tlist1);
246  expanding_redir = 0;
247  dispose_words (tlist1);
248
249  if (!tlist2 || tlist2->next)
250    {
251      /* We expanded to no words, or to more than a single word.
252	 Dispose of the word list and return NULL. */
253      if (tlist2)
254	dispose_words (tlist2);
255      return ((char *)NULL);
256    }
257  result = string_list (tlist2);  /* XXX savestring (tlist2->word->word)? */
258  dispose_words (tlist2);
259  return (result);
260}
261
262static int
263write_here_string (fd, redirectee)
264     int fd;
265     WORD_DESC *redirectee;
266{
267  char *herestr;
268  int herelen, n, e;
269
270  herestr = expand_string_to_string (redirectee->word, 0);
271  herelen = STRLEN (herestr);
272
273  n = write (fd, herestr, herelen);
274  if (n == herelen)
275    {
276      n = write (fd, "\n", 1);
277      herelen = 1;
278    }
279  e = errno;
280  FREE (herestr);
281  if (n != herelen)
282    {
283      if (e == 0)
284	e = ENOSPC;
285      return e;
286    }
287  return 0;
288}
289
290/* Write the text of the here document pointed to by REDIRECTEE to the file
291   descriptor FD, which is already open to a temp file.  Return 0 if the
292   write is successful, otherwise return errno. */
293static int
294write_here_document (fd, redirectee)
295     int fd;
296     WORD_DESC *redirectee;
297{
298  char *document;
299  int document_len, fd2;
300  FILE *fp;
301  register WORD_LIST *t, *tlist;
302
303  /* Expand the text if the word that was specified had
304     no quoting.  The text that we expand is treated
305     exactly as if it were surrounded by double quotes. */
306
307  if (redirectee->flags & W_QUOTED)
308    {
309      document = redirectee->word;
310      document_len = strlen (document);
311      /* Set errno to something reasonable if the write fails. */
312      if (write (fd, document, document_len) < document_len)
313	{
314	  if (errno == 0)
315	    errno = ENOSPC;
316	  return (errno);
317	}
318      else
319	return 0;
320    }
321
322  tlist = expand_string (redirectee->word, Q_HERE_DOCUMENT);
323  if (tlist)
324    {
325      /* Try using buffered I/O (stdio) and writing a word
326	 at a time, letting stdio do the work of buffering
327	 for us rather than managing our own strings.  Most
328	 stdios are not particularly fast, however -- this
329	 may need to be reconsidered later. */
330      if ((fd2 = dup (fd)) < 0 || (fp = fdopen (fd2, "w")) == NULL)
331	{
332	  if (fd2 >= 0)
333	    close (fd2);
334	  return (errno);
335	}
336      errno = 0;
337      for (t = tlist; t; t = t->next)
338	{
339	  /* This is essentially the body of
340	     string_list_internal expanded inline. */
341	  document = t->word->word;
342	  document_len = strlen (document);
343	  if (t != tlist)
344	    putc (' ', fp);	/* separator */
345	  fwrite (document, document_len, 1, fp);
346	  if (ferror (fp))
347	    {
348	      if (errno == 0)
349		errno = ENOSPC;
350	      fd2 = errno;
351	      fclose(fp);
352	      dispose_words (tlist);
353	      return (fd2);
354	    }
355	}
356      dispose_words (tlist);
357      if (fclose (fp) != 0)
358	{
359	  if (errno == 0)
360	    errno = ENOSPC;
361	  return (errno);
362	}
363    }
364  return 0;
365}
366
367/* Create a temporary file holding the text of the here document pointed to
368   by REDIRECTEE, and return a file descriptor open for reading to the temp
369   file.  Return -1 on any error, and make sure errno is set appropriately. */
370static int
371here_document_to_fd (redirectee, ri)
372     WORD_DESC *redirectee;
373     enum r_instruction ri;
374{
375  char *filename;
376  int r, fd, fd2;
377
378  fd = sh_mktmpfd ("sh-thd", MT_USERANDOM, &filename);
379
380  /* If we failed for some reason other than the file existing, abort */
381  if (fd < 0)
382    {
383      FREE (filename);
384      return (fd);
385    }
386
387  errno = r = 0;		/* XXX */
388  /* write_here_document returns 0 on success, errno on failure. */
389  if (redirectee->word)
390    r = (ri != r_reading_string) ? write_here_document (fd, redirectee)
391				 : write_here_string (fd, redirectee);
392
393  if (r)
394    {
395      close (fd);
396      unlink (filename);
397      free (filename);
398      errno = r;
399      return (-1);
400    }
401
402  /* In an attempt to avoid races, we close the first fd only after opening
403     the second. */
404  /* Make the document really temporary.  Also make it the input. */
405  fd2 = open (filename, O_RDONLY, 0600);
406
407  if (fd2 < 0)
408    {
409      r = errno;
410      unlink (filename);
411      free (filename);
412      close (fd);
413      errno = r;
414      return -1;
415    }
416
417  close (fd);
418  if (unlink (filename) < 0)
419    {
420      r = errno;
421#if defined (__CYGWIN__)
422      /* Under CygWin 1.1.0, the unlink will fail if the file is
423	 open. This hack will allow the previous action of silently
424	 ignoring the error, but will still leave the file there. This
425	 needs some kind of magic. */
426      if (r == EACCES)
427	return (fd2);
428#endif /* __CYGWIN__ */
429      close (fd2);
430      free (filename);
431      errno = r;
432      return (-1);
433    }
434
435  free (filename);
436  return (fd2);
437}
438
439#define RF_DEVFD	1
440#define RF_DEVSTDERR	2
441#define RF_DEVSTDIN	3
442#define RF_DEVSTDOUT	4
443#define RF_DEVTCP	5
444#define RF_DEVUDP	6
445
446/* A list of pattern/value pairs for filenames that the redirection
447   code handles specially. */
448static STRING_INT_ALIST _redir_special_filenames[] = {
449#if !defined (HAVE_DEV_FD)
450  { "/dev/fd/[0-9]*", RF_DEVFD },
451#endif
452#if !defined (HAVE_DEV_STDIN)
453  { "/dev/stderr", RF_DEVSTDERR },
454  { "/dev/stdin", RF_DEVSTDIN },
455  { "/dev/stdout", RF_DEVSTDOUT },
456#endif
457#if defined (NETWORK_REDIRECTIONS)
458  { "/dev/tcp/*/*", RF_DEVTCP },
459  { "/dev/udp/*/*", RF_DEVUDP },
460#endif
461  { (char *)NULL, -1 }
462};
463
464static int
465redir_special_open (spec, filename, flags, mode, ri)
466     int spec;
467     char *filename;
468     int flags, mode;
469     enum r_instruction ri;
470{
471  int fd;
472#if !defined (HAVE_DEV_FD)
473  intmax_t lfd;
474#endif
475
476  fd = -1;
477  switch (spec)
478    {
479#if !defined (HAVE_DEV_FD)
480    case RF_DEVFD:
481      if (all_digits (filename+8) && legal_number (filename+8, &lfd) && lfd == (int)lfd)
482	{
483	  fd = lfd;
484	  fd = fcntl (fd, F_DUPFD, 10);
485	}
486      else
487	fd = AMBIGUOUS_REDIRECT;
488      break;
489#endif
490
491#if !defined (HAVE_DEV_STDIN)
492    case RF_DEVSTDIN:
493      fd = fcntl (0, F_DUPFD, 10);
494      break;
495    case RF_DEVSTDOUT:
496      fd = fcntl (1, F_DUPFD, 10);
497      break;
498    case RF_DEVSTDERR:
499      fd = fcntl (2, F_DUPFD, 10);
500      break;
501#endif
502
503#if defined (NETWORK_REDIRECTIONS)
504    case RF_DEVTCP:
505    case RF_DEVUDP:
506#if defined (HAVE_NETWORK)
507      fd = netopen (filename);
508#else
509      internal_warning (_("/dev/(tcp|udp)/host/port not supported without networking"));
510      fd = open (filename, flags, mode);
511#endif
512      break;
513#endif /* NETWORK_REDIRECTIONS */
514    }
515
516  return fd;
517}
518
519/* Open FILENAME with FLAGS in noclobber mode, hopefully avoiding most
520   race conditions and avoiding the problem where the file is replaced
521   between the stat(2) and open(2). */
522static int
523noclobber_open (filename, flags, mode, ri)
524     char *filename;
525     int flags, mode;
526     enum r_instruction ri;
527{
528  int r, fd;
529  struct stat finfo, finfo2;
530
531  /* If the file exists and is a regular file, return an error
532     immediately. */
533  r = stat (filename, &finfo);
534  if (r == 0 && (S_ISREG (finfo.st_mode)))
535    return (NOCLOBBER_REDIRECT);
536
537  /* If the file was not present (r != 0), make sure we open it
538     exclusively so that if it is created before we open it, our open
539     will fail.  Make sure that we do not truncate an existing file.
540     Note that we don't turn on O_EXCL unless the stat failed -- if
541     the file was not a regular file, we leave O_EXCL off. */
542  flags &= ~O_TRUNC;
543  if (r != 0)
544    {
545      fd = open (filename, flags|O_EXCL, mode);
546      return ((fd < 0 && errno == EEXIST) ? NOCLOBBER_REDIRECT : fd);
547    }
548  fd = open (filename, flags, mode);
549
550  /* If the open failed, return the file descriptor right away. */
551  if (fd < 0)
552    return (errno == EEXIST ? NOCLOBBER_REDIRECT : fd);
553
554  /* OK, the open succeeded, but the file may have been changed from a
555     non-regular file to a regular file between the stat and the open.
556     We are assuming that the O_EXCL open handles the case where FILENAME
557     did not exist and is symlinked to an existing file between the stat
558     and open. */
559
560  /* If we can open it and fstat the file descriptor, and neither check
561     revealed that it was a regular file, and the file has not been replaced,
562     return the file descriptor. */
563  if ((fstat (fd, &finfo2) == 0) && (S_ISREG (finfo2.st_mode) == 0) &&
564      r == 0 && (S_ISREG (finfo.st_mode) == 0) &&
565      same_file (filename, filename, &finfo, &finfo2))
566    return fd;
567
568  /* The file has been replaced.  badness. */
569  close (fd);
570  errno = EEXIST;
571  return (NOCLOBBER_REDIRECT);
572}
573
574static int
575redir_open (filename, flags, mode, ri)
576     char *filename;
577     int flags, mode;
578     enum r_instruction ri;
579{
580  int fd, r;
581
582  r = find_string_in_alist (filename, _redir_special_filenames, 1);
583  if (r >= 0)
584    return (redir_special_open (r, filename, flags, mode, ri));
585
586  /* If we are in noclobber mode, you are not allowed to overwrite
587     existing files.  Check before opening. */
588  if (noclobber && CLOBBERING_REDIRECT (ri))
589    {
590      fd = noclobber_open (filename, flags, mode, ri);
591      if (fd == NOCLOBBER_REDIRECT)
592	return (NOCLOBBER_REDIRECT);
593    }
594  else
595    {
596      fd = open (filename, flags, mode);
597#if defined (AFS)
598      if ((fd < 0) && (errno == EACCES))
599	{
600	  fd = open (filename, flags & ~O_CREAT, mode);
601	  errno = EACCES;	/* restore errno */
602	}
603#endif /* AFS */
604    }
605
606  return fd;
607}
608
609/* Do the specific redirection requested.  Returns errno or one of the
610   special redirection errors (*_REDIRECT) in case of error, 0 on success.
611   If flags & RX_ACTIVE is zero, then just do whatever is neccessary to
612   produce the appropriate side effects.   flags & RX_UNDOABLE, if non-zero,
613   says to remember how to undo each redirection.  If flags & RX_CLEXEC is
614   non-zero, then we set all file descriptors > 2 that we open to be
615   close-on-exec.  */
616static int
617do_redirection_internal (redirect, flags)
618     REDIRECT *redirect;
619     int flags;
620{
621  WORD_DESC *redirectee;
622  int redir_fd, fd, redirector, r, oflags;
623  intmax_t lfd;
624  char *redirectee_word;
625  enum r_instruction ri;
626  REDIRECT *new_redirect;
627
628  redirectee = redirect->redirectee.filename;
629  redir_fd = redirect->redirectee.dest;
630  redirector = redirect->redirector;
631  ri = redirect->instruction;
632
633  if (redirect->flags & RX_INTERNAL)
634    flags |= RX_INTERNAL;
635
636  if (TRANSLATE_REDIRECT (ri))
637    {
638      /* We have [N]>&WORD[-] or [N]<&WORD[-].  Expand WORD, then translate
639	 the redirection into a new one and continue. */
640      redirectee_word = redirection_expand (redirectee);
641
642      /* XXX - what to do with [N]<&$w- where w is unset or null?  ksh93
643	       closes N. */
644      if (redirectee_word == 0)
645	return (AMBIGUOUS_REDIRECT);
646      else if (redirectee_word[0] == '-' && redirectee_word[1] == '\0')
647	{
648	  rd.dest = 0;
649	  new_redirect = make_redirection (redirector, r_close_this, rd);
650	}
651      else if (all_digits (redirectee_word))
652	{
653	  if (legal_number (redirectee_word, &lfd) && (int)lfd == lfd)
654	    rd.dest = lfd;
655	  else
656	    rd.dest = -1;	/* XXX */
657	  switch (ri)
658	    {
659	    case r_duplicating_input_word:
660	      new_redirect = make_redirection (redirector, r_duplicating_input, rd);
661	      break;
662	    case r_duplicating_output_word:
663	      new_redirect = make_redirection (redirector, r_duplicating_output, rd);
664	      break;
665	    case r_move_input_word:
666	      new_redirect = make_redirection (redirector, r_move_input, rd);
667	      break;
668	    case r_move_output_word:
669	      new_redirect = make_redirection (redirector, r_move_output, rd);
670	      break;
671	    }
672	}
673      else if (ri == r_duplicating_output_word && redirector == 1)
674	{
675	  rd.filename = make_bare_word (redirectee_word);
676	  new_redirect = make_redirection (1, r_err_and_out, rd);
677	}
678      else
679	{
680	  free (redirectee_word);
681	  return (AMBIGUOUS_REDIRECT);
682	}
683
684      free (redirectee_word);
685
686      /* Set up the variables needed by the rest of the function from the
687	 new redirection. */
688      if (new_redirect->instruction == r_err_and_out)
689	{
690	  char *alloca_hack;
691
692	  /* Copy the word without allocating any memory that must be
693	     explicitly freed. */
694	  redirectee = (WORD_DESC *)alloca (sizeof (WORD_DESC));
695	  xbcopy ((char *)new_redirect->redirectee.filename,
696		 (char *)redirectee, sizeof (WORD_DESC));
697
698	  alloca_hack = (char *)
699	    alloca (1 + strlen (new_redirect->redirectee.filename->word));
700	  redirectee->word = alloca_hack;
701	  strcpy (redirectee->word, new_redirect->redirectee.filename->word);
702	}
703      else
704	/* It's guaranteed to be an integer, and shouldn't be freed. */
705	redirectee = new_redirect->redirectee.filename;
706
707      redir_fd = new_redirect->redirectee.dest;
708      redirector = new_redirect->redirector;
709      ri = new_redirect->instruction;
710
711      /* Overwrite the flags element of the old redirect with the new value. */
712      redirect->flags = new_redirect->flags;
713      dispose_redirects (new_redirect);
714    }
715
716  switch (ri)
717    {
718    case r_output_direction:
719    case r_appending_to:
720    case r_input_direction:
721    case r_inputa_direction:
722    case r_err_and_out:		/* command &>filename */
723    case r_input_output:
724    case r_output_force:
725      if (posixly_correct && interactive_shell == 0)
726	{
727	  oflags = redirectee->flags;
728	  redirectee->flags |= W_NOGLOB;
729	}
730      redirectee_word = redirection_expand (redirectee);
731      if (posixly_correct && interactive_shell == 0)
732	redirectee->flags = oflags;
733
734      if (redirectee_word == 0)
735	return (AMBIGUOUS_REDIRECT);
736
737#if defined (RESTRICTED_SHELL)
738      if (restricted && (WRITE_REDIRECT (ri)))
739	{
740	  free (redirectee_word);
741	  return (RESTRICTED_REDIRECT);
742	}
743#endif /* RESTRICTED_SHELL */
744
745      fd = redir_open (redirectee_word, redirect->flags, 0666, ri);
746      free (redirectee_word);
747
748      if (fd == NOCLOBBER_REDIRECT)
749	return (fd);
750
751      if (fd < 0)
752	return (errno);
753
754      if (flags & RX_ACTIVE)
755	{
756	  if (flags & RX_UNDOABLE)
757	    {
758	      /* Only setup to undo it if the thing to undo is active. */
759	      if ((fd != redirector) && (fcntl (redirector, F_GETFD, 0) != -1))
760		add_undo_redirect (redirector, ri);
761	      else
762		add_undo_close_redirect (redirector);
763	    }
764
765#if defined (BUFFERED_INPUT)
766	  check_bash_input (redirector);
767#endif
768
769	  if ((fd != redirector) && (dup2 (fd, redirector) < 0))
770	    return (errno);
771
772#if defined (BUFFERED_INPUT)
773	  /* Do not change the buffered stream for an implicit redirection
774	     of /dev/null to fd 0 for asynchronous commands without job
775	     control (r_inputa_direction). */
776	  if (ri == r_input_direction || ri == r_input_output)
777	    duplicate_buffered_stream (fd, redirector);
778#endif /* BUFFERED_INPUT */
779
780	  /*
781	   * If we're remembering, then this is the result of a while, for
782	   * or until loop with a loop redirection, or a function/builtin
783	   * executing in the parent shell with a redirection.  In the
784	   * function/builtin case, we want to set all file descriptors > 2
785	   * to be close-on-exec to duplicate the effect of the old
786	   * for i = 3 to NOFILE close(i) loop.  In the case of the loops,
787	   * both sh and ksh leave the file descriptors open across execs.
788	   * The Posix standard mentions only the exec builtin.
789	   */
790	  if ((flags & RX_CLEXEC) && (redirector > 2))
791	    SET_CLOSE_ON_EXEC (redirector);
792	}
793
794      if (fd != redirector)
795	{
796#if defined (BUFFERED_INPUT)
797	  if (INPUT_REDIRECT (ri))
798	    close_buffered_fd (fd);
799	  else
800#endif /* !BUFFERED_INPUT */
801	    close (fd);		/* Don't close what we just opened! */
802	}
803
804      /* If we are hacking both stdout and stderr, do the stderr
805	 redirection here. */
806      if (ri == r_err_and_out)
807	{
808	  if (flags & RX_ACTIVE)
809	    {
810	      if (flags & RX_UNDOABLE)
811		add_undo_redirect (2, ri);
812	      if (dup2 (1, 2) < 0)
813		return (errno);
814	    }
815	}
816      break;
817
818    case r_reading_until:
819    case r_deblank_reading_until:
820    case r_reading_string:
821      /* REDIRECTEE is a pointer to a WORD_DESC containing the text of
822	 the new input.  Place it in a temporary file. */
823      if (redirectee)
824	{
825	  fd = here_document_to_fd (redirectee, ri);
826
827	  if (fd < 0)
828	    {
829	      heredoc_errno = errno;
830	      return (HEREDOC_REDIRECT);
831	    }
832
833	  if (flags & RX_ACTIVE)
834	    {
835	      if (flags & RX_UNDOABLE)
836	        {
837		  /* Only setup to undo it if the thing to undo is active. */
838		  if ((fd != redirector) && (fcntl (redirector, F_GETFD, 0) != -1))
839		    add_undo_redirect (redirector, ri);
840		  else
841		    add_undo_close_redirect (redirector);
842	        }
843
844#if defined (BUFFERED_INPUT)
845	      check_bash_input (redirector);
846#endif
847	      if (fd != redirector && dup2 (fd, redirector) < 0)
848		{
849		  r = errno;
850		  close (fd);
851		  return (r);
852		}
853
854#if defined (BUFFERED_INPUT)
855	      duplicate_buffered_stream (fd, redirector);
856#endif
857
858	      if ((flags & RX_CLEXEC) && (redirector > 2))
859		SET_CLOSE_ON_EXEC (redirector);
860	    }
861
862	  if (fd != redirector)
863#if defined (BUFFERED_INPUT)
864	    close_buffered_fd (fd);
865#else
866	    close (fd);
867#endif
868	}
869      break;
870
871    case r_duplicating_input:
872    case r_duplicating_output:
873    case r_move_input:
874    case r_move_output:
875      if ((flags & RX_ACTIVE) && (redir_fd != redirector))
876	{
877	  if (flags & RX_UNDOABLE)
878	    {
879	      /* Only setup to undo it if the thing to undo is active. */
880	      if (fcntl (redirector, F_GETFD, 0) != -1)
881		add_undo_redirect (redirector, ri);
882	      else
883		add_undo_close_redirect (redirector);
884	    }
885
886#if defined (BUFFERED_INPUT)
887	  check_bash_input (redirector);
888#endif
889	  /* This is correct.  2>&1 means dup2 (1, 2); */
890	  if (dup2 (redir_fd, redirector) < 0)
891	    return (errno);
892
893#if defined (BUFFERED_INPUT)
894	  if (ri == r_duplicating_input || ri == r_move_input)
895	    duplicate_buffered_stream (redir_fd, redirector);
896#endif /* BUFFERED_INPUT */
897
898	  /* First duplicate the close-on-exec state of redirectee.  dup2
899	     leaves the flag unset on the new descriptor, which means it
900	     stays open.  Only set the close-on-exec bit for file descriptors
901	     greater than 2 in any case, since 0-2 should always be open
902	     unless closed by something like `exec 2<&-'.  It should always
903	     be safe to set fds > 2 to close-on-exec if they're being used to
904	     save file descriptors < 2, since we don't need to preserve the
905	     state of the close-on-exec flag for those fds -- they should
906	     always be open. */
907	  /* if ((already_set || set_unconditionally) && (ok_to_set))
908		set_it () */
909#if 0
910	  if (((fcntl (redir_fd, F_GETFD, 0) == 1) || redir_fd < 2 || (flags & RX_CLEXEC)) &&
911	       (redirector > 2))
912#else
913	  if (((fcntl (redir_fd, F_GETFD, 0) == 1) || (redir_fd < 2 && (flags & RX_INTERNAL)) || (flags & RX_CLEXEC)) &&
914	       (redirector > 2))
915#endif
916	    SET_CLOSE_ON_EXEC (redirector);
917
918	  /* dup-and-close redirection */
919	  if (ri == r_move_input || ri == r_move_output)
920	    close (redir_fd);
921	}
922      break;
923
924    case r_close_this:
925      if (flags & RX_ACTIVE)
926	{
927	  if ((flags & RX_UNDOABLE) && (fcntl (redirector, F_GETFD, 0) != -1))
928	    add_undo_redirect (redirector, ri);
929
930#if defined (BUFFERED_INPUT)
931	  check_bash_input (redirector);
932	  close_buffered_fd (redirector);
933#else /* !BUFFERED_INPUT */
934	  close (redirector);
935#endif /* !BUFFERED_INPUT */
936	}
937      break;
938
939    case r_duplicating_input_word:
940    case r_duplicating_output_word:
941      break;
942    }
943  return (0);
944}
945
946#define SHELL_FD_BASE	10
947
948/* Remember the file descriptor associated with the slot FD,
949   on REDIRECTION_UNDO_LIST.  Note that the list will be reversed
950   before it is executed.  Any redirections that need to be undone
951   even if REDIRECTION_UNDO_LIST is discarded by the exec builtin
952   are also saved on EXEC_REDIRECTION_UNDO_LIST. */
953static int
954add_undo_redirect (fd, ri)
955     int fd;
956     enum r_instruction ri;
957{
958  int new_fd, clexec_flag;
959  REDIRECT *new_redirect, *closer, *dummy_redirect;
960
961  new_fd = fcntl (fd, F_DUPFD, SHELL_FD_BASE);
962
963  if (new_fd < 0)
964    {
965      sys_error (_("redirection error: cannot duplicate fd"));
966      return (-1);
967    }
968
969  clexec_flag = fcntl (fd, F_GETFD, 0);
970
971  rd.dest = 0;
972  closer = make_redirection (new_fd, r_close_this, rd);
973  closer->flags |= RX_INTERNAL;
974  dummy_redirect = copy_redirects (closer);
975
976  rd.dest = new_fd;
977  if (fd == 0)
978    new_redirect = make_redirection (fd, r_duplicating_input, rd);
979  else
980    new_redirect = make_redirection (fd, r_duplicating_output, rd);
981  new_redirect->flags |= RX_INTERNAL;
982  new_redirect->next = closer;
983
984  closer->next = redirection_undo_list;
985  redirection_undo_list = new_redirect;
986
987  /* Save redirections that need to be undone even if the undo list
988     is thrown away by the `exec' builtin. */
989  add_exec_redirect (dummy_redirect);
990
991  /* experimental:  if we're saving a redirection to undo for a file descriptor
992     above SHELL_FD_BASE, add a redirection to be undone if the exec builtin
993     causes redirections to be discarded. */
994  if (fd >= SHELL_FD_BASE && ri != r_close_this)
995    {
996      rd.dest = new_fd;
997      new_redirect = make_redirection (fd, r_duplicating_output, rd);
998#if 0
999      closer = copy_redirects (new_redirect);
1000      add_exec_redirect (closer);
1001#else
1002      add_exec_redirect (new_redirect);
1003#endif
1004    }
1005
1006  /* File descriptors used only for saving others should always be
1007     marked close-on-exec.  Unfortunately, we have to preserve the
1008     close-on-exec state of the file descriptor we are saving, since
1009     fcntl (F_DUPFD) sets the new file descriptor to remain open
1010     across execs.  If, however, the file descriptor whose state we
1011     are saving is <= 2, we can just set the close-on-exec flag,
1012     because file descriptors 0-2 should always be open-on-exec,
1013     and the restore above in do_redirection() will take care of it. */
1014  if (clexec_flag || fd < 3)
1015    SET_CLOSE_ON_EXEC (new_fd);
1016
1017  return (0);
1018}
1019
1020/* Set up to close FD when we are finished with the current command
1021   and its redirections. */
1022static void
1023add_undo_close_redirect (fd)
1024     int fd;
1025{
1026  REDIRECT *closer;
1027
1028  rd.dest = 0;
1029  closer = make_redirection (fd, r_close_this, rd);
1030  closer->flags |= RX_INTERNAL;
1031  closer->next = redirection_undo_list;
1032  redirection_undo_list = closer;
1033}
1034
1035static void
1036add_exec_redirect (dummy_redirect)
1037     REDIRECT *dummy_redirect;
1038{
1039  dummy_redirect->next = exec_redirection_undo_list;
1040  exec_redirection_undo_list = dummy_redirect;
1041}
1042
1043/* Return 1 if the redirection specified by RI and REDIRECTOR alters the
1044   standard input. */
1045static int
1046stdin_redirection (ri, redirector)
1047     enum r_instruction ri;
1048     int redirector;
1049{
1050  switch (ri)
1051    {
1052    case r_input_direction:
1053    case r_inputa_direction:
1054    case r_input_output:
1055    case r_reading_until:
1056    case r_deblank_reading_until:
1057    case r_reading_string:
1058      return (1);
1059    case r_duplicating_input:
1060    case r_duplicating_input_word:
1061    case r_close_this:
1062      return (redirector == 0);
1063    case r_output_direction:
1064    case r_appending_to:
1065    case r_duplicating_output:
1066    case r_err_and_out:
1067    case r_output_force:
1068    case r_duplicating_output_word:
1069      return (0);
1070    }
1071  return (0);
1072}
1073
1074/* Return non-zero if any of the redirections in REDIRS alter the standard
1075   input. */
1076int
1077stdin_redirects (redirs)
1078     REDIRECT *redirs;
1079{
1080  REDIRECT *rp;
1081  int n;
1082
1083  for (n = 0, rp = redirs; rp; rp = rp->next)
1084    n += stdin_redirection (rp->instruction, rp->redirector);
1085  return n;
1086}
1087