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