]> git.ipfire.org Git - thirdparty/bash.git/blob - shell.c
Imported from ../bash-2.03.tar.gz.
[thirdparty/bash.git] / shell.c
1 /* shell.c -- GNU's idea of the POSIX shell specification.
2
3 This file is part of Bash, the Bourne Again SHell. Bash is free
4 software; no one can prevent you from reading the source code, or
5 giving it to someone else. This file is copyrighted under the GNU
6 General Public License, which can be found in the file called
7 COPYING.
8
9 Copyright (C) 1988, 1991 Free Software Foundation, Inc.
10
11 This file is part of GNU Bash.
12
13 Bash is distributed in the hope that it will be useful, but WITHOUT
14 ANY WARRANTY. No author or distributor accepts responsibility to
15 anyone for the consequences of using it or for whether it serves
16 any particular purpose or works at all, unless he says so in
17 writing. Refer to the GNU Emacs General Public License for full
18 details.
19
20 Everyone is granted permission to copy, modify and redistribute
21 Bash, but only under the conditions described in the GNU General
22 Public License. A copy of this license is supposed to have been
23 given to you along with GNU Emacs so you can know your rights and
24 responsibilities. It should be in a file named COPYING.
25
26 Among other things, the copyright notice and this notice must be
27 preserved on all copies.
28
29 Birthdate:
30 Sunday, January 10th, 1988.
31 Initial author: Brian Fox
32 */
33 #define INSTALL_DEBUG_MODE
34
35 #include "config.h"
36
37 #include "bashtypes.h"
38 #ifndef _MINIX
39 # include <sys/file.h>
40 #endif
41 #include "posixstat.h"
42 #include "bashansi.h"
43 #include <stdio.h>
44 #include <signal.h>
45 #include <errno.h>
46 #include "filecntl.h"
47 #include <pwd.h>
48
49 #if defined (HAVE_UNISTD_H)
50 # include <unistd.h>
51 #endif
52
53 #include "shell.h"
54 #include "flags.h"
55 #include "trap.h"
56 #include "mailcheck.h"
57 #include "builtins.h"
58 #include "builtins/common.h"
59
60 #if defined (JOB_CONTROL)
61 #include "jobs.h"
62 #endif /* JOB_CONTROL */
63
64 #include "input.h"
65 #include "execute_cmd.h"
66 #include "findcmd.h"
67
68 #if defined (HISTORY)
69 # include "bashhist.h"
70 # include <readline/history.h>
71 #endif
72
73 #include <tilde/tilde.h>
74 #include <glob/fnmatch.h>
75
76 #if defined (__OPENNT)
77 # include <opennt/opennt.h>
78 #endif
79
80 #if !defined (HAVE_GETPW_DECLS)
81 extern struct passwd *getpwuid ();
82 #endif /* !HAVE_GETPW_DECLS */
83
84 #if !defined (errno)
85 extern int errno;
86 #endif
87
88 #if defined (NO_MAIN_ENV_ARG)
89 extern char **environ; /* used if no third argument to main() */
90 #endif
91
92 extern char *dist_version, *release_status;
93 extern int patch_level, build_version;
94 extern int subshell_environment;
95 extern int last_command_exit_value;
96 extern int line_number;
97 extern char *primary_prompt, *secondary_prompt;
98 extern int expand_aliases;
99 extern char *this_command_name;
100 extern int array_needs_making;
101
102 /* Non-zero means that this shell has already been run; i.e. you should
103 call shell_reinitialize () if you need to start afresh. */
104 int shell_initialized = 0;
105
106 COMMAND *global_command = (COMMAND *)NULL;
107
108 /* Information about the current user. */
109 struct user_info current_user =
110 {
111 -1, -1, -1, -1, (char *)NULL, (char *)NULL, (char *)NULL
112 };
113
114 /* The current host's name. */
115 char *current_host_name = (char *)NULL;
116
117 /* Non-zero means that this shell is a login shell.
118 Specifically:
119 0 = not login shell.
120 1 = login shell from getty (or equivalent fake out)
121 -1 = login shell from "--login" flag.
122 -2 = both from getty, and from flag.
123 */
124 int login_shell = 0;
125
126 /* Non-zero means that at this moment, the shell is interactive. In
127 general, this means that the shell is at this moment reading input
128 from the keyboard. */
129 int interactive = 0;
130
131 /* Non-zero means that the shell was started as an interactive shell. */
132 int interactive_shell = 0;
133
134 /* Non-zero means to send a SIGHUP to all jobs when an interactive login
135 shell exits. */
136 int hup_on_exit = 0;
137
138 /* Tells what state the shell was in when it started:
139 0 = non-interactive shell script
140 1 = interactive
141 2 = -c command
142 This is a superset of the information provided by interactive_shell.
143 */
144 int startup_state = 0;
145
146 /* Special debugging helper. */
147 int debugging_login_shell = 0;
148
149 /* The environment that the shell passes to other commands. */
150 char **shell_environment;
151
152 /* Non-zero when we are executing a top-level command. */
153 int executing = 0;
154
155 /* The number of commands executed so far. */
156 int current_command_number = 1;
157
158 /* Non-zero is the recursion depth for commands. */
159 int indirection_level = 0;
160
161 /* The name of this shell, as taken from argv[0]. */
162 char *shell_name = (char *)NULL;
163
164 /* time in seconds when the shell was started */
165 time_t shell_start_time;
166
167 /* Are we running in an emacs shell window? */
168 int running_under_emacs;
169
170 /* The name of the .(shell)rc file. */
171 static char *bashrc_file = "~/.bashrc";
172
173 /* Non-zero means to act more like the Bourne shell on startup. */
174 static int act_like_sh;
175
176 /* Non-zero if this shell is being run by `su'. */
177 static int su_shell;
178
179 /* Non-zero if we have already expanded and sourced $ENV. */
180 static int sourced_env;
181
182 /* Is this shell running setuid? */
183 static int running_setuid;
184
185 /* Values for the long-winded argument names. */
186 static int debugging; /* Do debugging things. */
187 static int no_rc; /* Don't execute ~/.bashrc */
188 static int no_profile; /* Don't execute .profile */
189 static int do_version; /* Display interesting version info. */
190 static int make_login_shell; /* Make this shell be a `-bash' shell. */
191 static int want_initial_help; /* --help option */
192
193 int no_line_editing = 0; /* Don't do fancy line editing. */
194 int posixly_correct = 0; /* Non-zero means posix.2 superset. */
195 int dump_translatable_strings; /* Dump strings in $"...", don't execute. */
196 int dump_po_strings; /* Dump strings in $"..." in po format */
197 int wordexp_only = 0; /* Do word expansion only */
198
199 /* Some long-winded argument names. These are obviously new. */
200 #define Int 1
201 #define Charp 2
202 struct {
203 char *name;
204 int type;
205 int *int_value;
206 char **char_value;
207 } long_args[] = {
208 { "debug", Int, &debugging, (char **)0x0 },
209 { "dump-po-strings", Int, &dump_po_strings, (char **)0x0 },
210 { "dump-strings", Int, &dump_translatable_strings, (char **)0x0 },
211 { "help", Int, &want_initial_help, (char **)0x0 },
212 { "login", Int, &make_login_shell, (char **)0x0 },
213 { "noediting", Int, &no_line_editing, (char **)0x0 },
214 { "noprofile", Int, &no_profile, (char **)0x0 },
215 { "norc", Int, &no_rc, (char **)0x0 },
216 { "posix", Int, &posixly_correct, (char **)0x0 },
217 { "rcfile", Charp, (int *)0x0, &bashrc_file },
218 #if defined (RESTRICTED_SHELL)
219 { "restricted", Int, &restricted, (char **)0x0 },
220 #endif
221 { "verbose", Int, &echo_input_at_read, (char **)0x0 },
222 { "version", Int, &do_version, (char **)0x0 },
223 { "wordexp", Int, &wordexp_only, (char **)0x0 },
224 { (char *)0x0, Int, (int *)0x0, (char **)0x0 }
225 };
226
227 /* These are extern so execute_simple_command can set them, and then
228 longjmp back to main to execute a shell script, instead of calling
229 main () again and resulting in indefinite, possibly fatal, stack
230 growth. */
231 procenv_t subshell_top_level;
232 int subshell_argc;
233 char **subshell_argv;
234 char **subshell_envp;
235
236 #if defined (BUFFERED_INPUT)
237 /* The file descriptor from which the shell is reading input. */
238 int default_buffered_input = -1;
239 #endif
240
241 static int read_from_stdin; /* -s flag supplied */
242 static int want_pending_command; /* -c flag supplied */
243 static char *local_pending_command;
244
245 static FILE *default_input;
246
247 static int parse_long_options ();
248 static int parse_shell_options ();
249 static void run_startup_files ();
250 static int bind_args ();
251 static int open_shell_script ();
252 static void set_bash_input ();
253 static int run_one_command ();
254 static int run_wordexp ();
255
256 static int uidget ();
257 static int isnetconn ();
258
259 static void init_interactive (), init_noninteractive ();
260 static void set_shell_name ();
261 static void shell_initialize ();
262 static void shell_reinitialize ();
263
264 static void show_shell_usage ();
265
266 #ifdef __CYGWIN32__
267 static void
268 _cygwin32_check_tmp ()
269 {
270 struct stat sb;
271
272 if (stat ("/tmp", &sb) < 0)
273 internal_warning ("could not find /tmp, please create!");
274 else
275 {
276 if (S_ISDIR (sb.st_mode) == 0)
277 internal_warning ("/tmp must be a valid directory name");
278 }
279 }
280 #endif /* __CYGWIN32__ */
281
282 #if defined (NO_MAIN_ENV_ARG)
283 /* systems without third argument to main() */
284 int
285 main (argc, argv)
286 int argc;
287 char **argv;
288 #else /* !NO_MAIN_ENV_ARG */
289 int
290 main (argc, argv, env)
291 int argc;
292 char **argv, **env;
293 #endif /* !NO_MAIN_ENV_ARG */
294 {
295 register int i;
296 int code, saverst, old_errexit_flag;
297 volatile int locally_skip_execution;
298 volatile int arg_index, top_level_arg_index;
299 #ifdef __OPENNT
300 char **env;
301
302 env = environ;
303 #endif /* __OPENNT */
304
305 /* Catch early SIGINTs. */
306 code = setjmp (top_level);
307 if (code)
308 exit (2);
309
310 check_dev_tty ();
311
312 #ifdef __CYGWIN32__
313 _cygwin32_check_tmp ();
314 #endif
315
316 /* Wait forever if we are debugging a login shell. */
317 while (debugging_login_shell);
318
319 set_default_locale ();
320
321 running_setuid = uidget ();
322
323 posixly_correct = (getenv ("POSIXLY_CORRECT") != (char *)NULL) ||
324 (getenv ("POSIX_PEDANTIC") != (char *)NULL);
325
326 #if defined (USE_GNU_MALLOC_LIBRARY)
327 mcheck (programming_error, (void (*) ())0);
328 #endif /* USE_GNU_MALLOC_LIBRARY */
329
330 if (setjmp (subshell_top_level))
331 {
332 argc = subshell_argc;
333 argv = subshell_argv;
334 env = subshell_envp;
335 sourced_env = 0;
336 }
337
338 /* Initialize `local' variables for all `invocations' of main (). */
339 arg_index = 1;
340 local_pending_command = (char *)NULL;
341 want_pending_command = locally_skip_execution = read_from_stdin = 0;
342 default_input = stdin;
343 #if defined (BUFFERED_INPUT)
344 default_buffered_input = -1;
345 #endif
346
347 /* Fix for the `infinite process creation' bug when running shell scripts
348 from startup files on System V. */
349 login_shell = make_login_shell = 0;
350
351 /* If this shell has already been run, then reinitialize it to a
352 vanilla state. */
353 if (shell_initialized || shell_name)
354 {
355 /* Make sure that we do not infinitely recurse as a login shell. */
356 if (*shell_name == '-')
357 shell_name++;
358
359 shell_reinitialize ();
360 if (setjmp (top_level))
361 exit (2);
362 }
363
364 shell_environment = env;
365 set_shell_name (argv[0]);
366 shell_start_time = NOW; /* NOW now defined in general.h */
367
368 /* Parse argument flags from the input line. */
369
370 /* Find full word arguments first. */
371 arg_index = parse_long_options (argv, arg_index, argc);
372
373 if (want_initial_help)
374 {
375 show_shell_usage (stdout, 1);
376 exit (EXECUTION_SUCCESS);
377 }
378
379 if (do_version)
380 {
381 show_shell_version (1);
382 exit (EXECUTION_SUCCESS);
383 }
384
385 /* If user supplied the "--login" flag, then set and invert LOGIN_SHELL. */
386 if (make_login_shell)
387 {
388 login_shell++;
389 login_shell = -login_shell;
390 }
391
392 /* All done with full word options; do standard shell option parsing.*/
393 this_command_name = shell_name; /* for error reporting */
394 arg_index = parse_shell_options (argv, arg_index, argc);
395
396 if (dump_po_strings)
397 dump_translatable_strings = 1;
398
399 if (dump_translatable_strings)
400 read_but_dont_execute = 1;
401
402 if (running_setuid && privileged_mode == 0)
403 disable_priv_mode ();
404
405 /* Need to get the argument to a -c option processed in the
406 above loop. The next arg is a command to execute, and the
407 following args are $0...$n respectively. */
408 if (want_pending_command)
409 {
410 local_pending_command = argv[arg_index];
411 if (local_pending_command == 0)
412 {
413 report_error ("option `-c' requires an argument");
414 exit (EX_USAGE);
415 }
416 arg_index++;
417 }
418 this_command_name = (char *)NULL;
419
420 /* First, let the outside world know about our interactive status.
421 A shell is interactive if the `-i' flag was given, or if all of
422 the following conditions are met:
423 no -c command
424 no arguments remaining or the -s flag given
425 standard input is a terminal
426 standard output is a terminal
427 Refer to Posix.2, the description of the `sh' utility. */
428
429 if (forced_interactive || /* -i flag */
430 (!local_pending_command && /* No -c command and ... */
431 wordexp_only == 0 && /* No --wordexp and ... */
432 ((arg_index == argc) || /* no remaining args or... */
433 read_from_stdin) && /* -s flag with args, and */
434 isatty (fileno (stdin)) && /* Input is a terminal and */
435 isatty (fileno (stdout)))) /* output is a terminal. */
436 init_interactive ();
437 else
438 init_noninteractive ();
439
440 #define CLOSE_FDS_AT_LOGIN
441 #if defined (CLOSE_FDS_AT_LOGIN)
442 /*
443 * Some systems have the bad habit of starting login shells with lots of open
444 * file descriptors. For instance, most systems that have picked up the
445 * pre-4.0 Sun YP code leave a file descriptor open each time you call one
446 * of the getpw* functions, and it's set to be open across execs. That
447 * means one for login, one for xterm, one for shelltool, etc.
448 */
449 if (login_shell && interactive_shell)
450 {
451 for (i = 3; i < 20; i++)
452 close (i);
453 }
454 #endif /* CLOSE_FDS_AT_LOGIN */
455
456 /* If we're in a strict Posix.2 mode, turn on interactive comments and
457 other Posix.2 things. */
458 if (posixly_correct)
459 {
460 posix_initialize (posixly_correct);
461 #if defined (READLINE)
462 if (interactive_shell)
463 posix_readline_initialize (posixly_correct);
464 #endif
465 }
466
467 /* From here on in, the shell must be a normal functioning shell.
468 Variables from the environment are expected to be set, etc. */
469 shell_initialize ();
470
471 set_default_locale_vars ();
472
473 if (interactive_shell)
474 {
475 char *term;
476
477 term = getenv ("TERM");
478 no_line_editing |= term && (STREQ (term, "emacs"));
479 term = getenv ("EMACS");
480 running_under_emacs = term ? ((fnmatch ("*term*", term, 0) == 0) ? 2 : 1)
481 : 0;
482 }
483
484 top_level_arg_index = arg_index;
485 old_errexit_flag = exit_immediately_on_error;
486
487 /* Give this shell a place to longjmp to before executing the
488 startup files. This allows users to press C-c to abort the
489 lengthy startup. */
490 code = setjmp (top_level);
491 if (code)
492 {
493 if (code == EXITPROG)
494 exit_shell (last_command_exit_value);
495 else
496 {
497 #if defined (JOB_CONTROL)
498 /* Reset job control, since run_startup_files turned it off. */
499 set_job_control (interactive_shell);
500 #endif
501 /* Reset value of `set -e', since it's turned off before running
502 the startup files. */
503 exit_immediately_on_error += old_errexit_flag;
504 locally_skip_execution++;
505 }
506 }
507
508 arg_index = top_level_arg_index;
509
510 /* Execute the start-up scripts. */
511
512 if (interactive_shell == 0)
513 {
514 makunbound ("PS1", shell_variables);
515 makunbound ("PS2", shell_variables);
516 interactive = expand_aliases = 0;
517 }
518 else
519 {
520 change_flag ('i', FLAG_ON);
521 interactive = 1;
522 }
523
524 #if defined (RESTRICTED_SHELL)
525 /* Set restricted_shell based on whether the basename of $0 indicates that
526 the shell should be restricted or if the `-r' option was supplied at
527 startup. */
528 restricted_shell = shell_is_restricted (shell_name);
529
530 /* If the `-r' option is supplied at invocation, make sure that the shell
531 is not in restricted mode when running the startup files. */
532 saverst = restricted;
533 restricted = 0;
534 #endif
535
536 /* The startup files are run with `set -e' temporarily disabled. */
537 if (locally_skip_execution == 0 && running_setuid == 0)
538 {
539 old_errexit_flag = exit_immediately_on_error;
540 exit_immediately_on_error = 0;
541
542 run_startup_files ();
543
544 exit_immediately_on_error += old_errexit_flag;
545 }
546
547 /* If we are invoked as `sh', turn on Posix mode. */
548 if (act_like_sh)
549 {
550 posix_initialize (posixly_correct = 1);
551 #if defined (READLINE)
552 if (interactive_shell)
553 posix_readline_initialize (posixly_correct);
554 #endif
555 }
556
557 #if defined (RESTRICTED_SHELL)
558 /* Turn on the restrictions after executing the startup files. This
559 means that `bash -r' or `set -r' invoked from a startup file will
560 turn on the restrictions after the startup files are executed. */
561 restricted = saverst || restricted;
562 maybe_make_restricted (shell_name);
563 #endif /* RESTRICTED_SHELL */
564
565 if (wordexp_only)
566 {
567 startup_state = 3;
568 last_command_exit_value = run_wordexp (argv[arg_index]);
569 exit_shell (last_command_exit_value);
570 }
571
572 if (local_pending_command)
573 {
574 arg_index = bind_args (argv, arg_index, argc, 0);
575
576 startup_state = 2;
577 #if defined (ONESHOT)
578 run_one_command (local_pending_command);
579 exit_shell (last_command_exit_value);
580 #else /* ONESHOT */
581 with_input_from_string (local_pending_command, "-c");
582 goto read_and_execute;
583 #endif /* !ONESHOT */
584 }
585
586 /* Get possible input filename and set up default_buffered_input or
587 default_input as appropriate. */
588 if (arg_index != argc && read_from_stdin == 0)
589 {
590 open_shell_script (argv[arg_index]);
591 arg_index++;
592 }
593 else if (interactive == 0)
594 /* In this mode, bash is reading a script from stdin, which is a
595 pipe or redirected file. */
596 #if defined (BUFFERED_INPUT)
597 default_buffered_input = fileno (stdin); /* == 0 */
598 #else
599 setbuf (default_input, (char *)NULL);
600 #endif /* !BUFFERED_INPUT */
601
602 set_bash_input ();
603
604 /* Bind remaining args to $1 ... $n */
605 arg_index = bind_args (argv, arg_index, argc, 1);
606
607 /* Do the things that should be done only for interactive shells. */
608 if (interactive_shell)
609 {
610 /* Set up for checking for presence of mail. */
611 remember_mail_dates ();
612 reset_mail_timer ();
613
614 #if defined (HISTORY)
615 /* Initialize the interactive history stuff. */
616 bash_initialize_history ();
617 if (shell_initialized == 0)
618 load_history ();
619 #endif /* HISTORY */
620
621 /* Initialize terminal state for interactive shells after the
622 .bash_profile and .bashrc are interpreted. */
623 get_tty_state ();
624 }
625
626 #if !defined (ONESHOT)
627 read_and_execute:
628 #endif /* !ONESHOT */
629
630 shell_initialized = 1;
631
632 /* Read commands until exit condition. */
633 reader_loop ();
634 exit_shell (last_command_exit_value);
635 }
636
637 static int
638 parse_long_options (argv, arg_start, arg_end)
639 char **argv;
640 int arg_start, arg_end;
641 {
642 int arg_index, longarg, i;
643 char *arg_string;
644
645 arg_index = arg_start;
646 while ((arg_index != arg_end) && (arg_string = argv[arg_index]) &&
647 (*arg_string == '-'))
648 {
649 longarg = 0;
650
651 /* Make --login equivalent to -login. */
652 if (arg_string[1] == '-' && arg_string[2])
653 {
654 longarg = 1;
655 arg_string++;
656 }
657
658 for (i = 0; long_args[i].name; i++)
659 {
660 if (STREQ (arg_string + 1, long_args[i].name))
661 {
662 if (long_args[i].type == Int)
663 *long_args[i].int_value = 1;
664 else if (argv[++arg_index] == 0)
665 {
666 report_error ("option `%s' requires an argument",
667 long_args[i].name);
668 exit (EX_USAGE);
669 }
670 else
671 *long_args[i].char_value = argv[arg_index];
672
673 break;
674 }
675 }
676 if (long_args[i].name == 0)
677 {
678 if (longarg)
679 {
680 report_error ("%s: unrecognized option", argv[arg_index]);
681 show_shell_usage (stderr, 0);
682 exit (EX_USAGE);
683 }
684 break; /* No such argument. Maybe flag arg. */
685 }
686
687 arg_index++;
688 }
689
690 return (arg_index);
691 }
692
693 static int
694 parse_shell_options (argv, arg_start, arg_end)
695 char **argv;
696 int arg_start, arg_end;
697 {
698 int arg_index;
699 int arg_character, on_or_off, next_arg, i;
700 char *o_option, *arg_string;
701
702 arg_index = arg_start;
703 while (arg_index != arg_end && (arg_string = argv[arg_index]) &&
704 (*arg_string == '-' || *arg_string == '+'))
705 {
706 /* There are flag arguments, so parse them. */
707 next_arg = arg_index + 1;
708
709 /* A single `-' signals the end of options. From the 4.3 BSD sh.
710 An option `--' means the same thing; this is the standard
711 getopt(3) meaning. */
712 if (arg_string[0] == '-' &&
713 (arg_string[1] == '\0' ||
714 (arg_string[1] == '-' && arg_string[2] == '\0')))
715 return (next_arg);
716
717 i = 1;
718 on_or_off = arg_string[0];
719 while (arg_character = arg_string[i++])
720 {
721 switch (arg_character)
722 {
723 case 'c':
724 want_pending_command = 1;
725 break;
726
727 case 's':
728 read_from_stdin = 1;
729 break;
730
731 case 'o':
732 o_option = argv[next_arg];
733 if (o_option == 0)
734 {
735 list_minus_o_opts (-1, (on_or_off == '-') ? 0 : 1);
736 break;
737 }
738 if (set_minus_o_option (on_or_off, o_option) != EXECUTION_SUCCESS)
739 exit (EX_USAGE);
740 next_arg++;
741 break;
742
743 case 'D':
744 dump_translatable_strings = 1;
745 break;
746
747 default:
748 if (change_flag (arg_character, on_or_off) == FLAG_ERROR)
749 {
750 report_error ("%c%c: unrecognized option", on_or_off, arg_character);
751 show_shell_usage (stderr, 0);
752 exit (EX_USAGE);
753 }
754 }
755 }
756 /* Can't do just a simple increment anymore -- what about
757 "bash -abouo emacs ignoreeof -hP"? */
758 arg_index = next_arg;
759 }
760
761 return (arg_index);
762 }
763
764 /* Exit the shell with status S. */
765 void
766 exit_shell (s)
767 int s;
768 {
769 /* Do trap[0] if defined. Allow it to override the exit status
770 passed to us. */
771 if (signal_is_trapped (0))
772 s = run_exit_trap ();
773
774 #if defined (PROCESS_SUBSTITUTION)
775 unlink_fifo_list ();
776 #endif /* PROCESS_SUBSTITUTION */
777
778 #if defined (HISTORY)
779 if (interactive_shell)
780 maybe_save_shell_history ();
781 #endif /* HISTORY */
782
783 #if defined (JOB_CONTROL)
784 /* If the user has run `shopt -s huponexit', hangup all jobs when we exit
785 an interactive login shell. ksh does this unconditionally. */
786 if (interactive_shell && login_shell && hup_on_exit)
787 hangup_all_jobs ();
788
789 /* If this shell is interactive, terminate all stopped jobs and
790 restore the original terminal process group. */
791 end_job_control ();
792 #endif /* JOB_CONTROL */
793
794 /* Always return the exit status of the last command to our parent. */
795 exit (s);
796 }
797
798 /* Source the bash startup files. If POSIXLY_CORRECT is non-zero, we obey
799 the Posix.2 startup file rules: $ENV is expanded, and if the file it
800 names exists, that file is sourced. The Posix.2 rules are in effect
801 for interactive shells only. (section 4.56.5.3) */
802
803 /* Execute ~/.bashrc for most shells. Never execute it if
804 ACT_LIKE_SH is set, or if NO_RC is set.
805
806 If the executable file "/usr/gnu/src/bash/foo" contains:
807
808 #!/usr/gnu/bin/bash
809 echo hello
810
811 then:
812
813 COMMAND EXECUTE BASHRC
814 --------------------------------
815 bash -c foo NO
816 bash foo NO
817 foo NO
818 rsh machine ls YES (for rsh, which calls `bash -c')
819 rsh machine foo YES (for shell started by rsh) NO (for foo!)
820 echo ls | bash NO
821 login NO
822 bash YES
823 */
824
825 static void
826 execute_env_file (env_file)
827 char *env_file;
828 {
829 char *fn;
830 WORD_LIST *list;
831
832 if (env_file && *env_file)
833 {
834 list = expand_string_unsplit (env_file, Q_DOUBLE_QUOTES);
835 if (list)
836 {
837 fn = string_list (list);
838 dispose_words (list);
839
840 if (fn && *fn)
841 maybe_execute_file (fn, 1);
842 FREE (fn);
843 }
844 }
845 }
846
847 static void
848 run_startup_files ()
849 {
850 #if defined (JOB_CONTROL)
851 int old_job_control;
852 #endif
853 int sourced_login, run_by_ssh;
854 SHELL_VAR *sshvar;
855
856 /* get the rshd/sshd case out of the way first. */
857 if (interactive_shell == 0 && no_rc == 0 && login_shell == 0 &&
858 act_like_sh == 0 && local_pending_command)
859 {
860 /* Find out if we were invoked by ssh. If so, set RUN_BY_SSH to 1. */
861 sshvar = find_variable ("SSH_CLIENT");
862 if (sshvar)
863 {
864 run_by_ssh = 1;
865 /* Now that we've tested the variable, we need to unexport it. */
866 sshvar->attributes &= ~att_exported;
867 array_needs_making = 1;
868 }
869 else
870 run_by_ssh = 0;
871
872 /* If we were run by sshd or we think we were run by rshd, execute
873 ~/.bashrc. */
874 if (run_by_ssh || isnetconn (fileno (stdin)))
875 {
876 #ifdef SYS_BASHRC
877 # if defined (__OPENNT)
878 maybe_execute_file (_prefixInstallPath(SYS_BASHRC, NULL, 0), 1);
879 # else
880 maybe_execute_file (SYS_BASHRC, 1);
881 # endif
882 #endif
883 maybe_execute_file (bashrc_file, 1);
884 return;
885 }
886 }
887
888 #if defined (JOB_CONTROL)
889 /* Startup files should be run without job control enabled. */
890 old_job_control = interactive_shell ? set_job_control (0) : 0;
891 #endif
892
893 sourced_login = 0;
894
895 if (login_shell < 0 && posixly_correct == 0) /* --login flag and not posix */
896 {
897 /* We don't execute .bashrc for login shells. */
898 no_rc++;
899
900 /* Execute /etc/profile and one of the personal login shell
901 initialization files. */
902 if (no_profile == 0)
903 {
904 maybe_execute_file (SYS_PROFILE, 1);
905
906 if (act_like_sh) /* sh */
907 maybe_execute_file ("~/.profile", 1);
908 else if ((maybe_execute_file ("~/.bash_profile", 1) == 0) &&
909 (maybe_execute_file ("~/.bash_login", 1) == 0)) /* bash */
910 maybe_execute_file ("~/.profile", 1);
911 }
912
913 sourced_login = 1;
914 }
915
916 /* A non-interactive shell not named `sh' and not in posix mode reads and
917 executes commands from $BASH_ENV. If `su' starts a shell with `-c cmd'
918 and `-su' as the name of the shell, we want to read the startup files.
919 No other non-interactive shells read any startup files. */
920 if (interactive_shell == 0 && !(su_shell && login_shell))
921 {
922 if (posixly_correct == 0 && act_like_sh == 0 && privileged_mode == 0 &&
923 sourced_env++ == 0)
924 execute_env_file (get_string_value ("BASH_ENV"));
925 return;
926 }
927
928 /* Interactive shell or `-su' shell. */
929 if (posixly_correct == 0) /* bash, sh */
930 {
931 if (login_shell && sourced_login++ == 0)
932 {
933 /* We don't execute .bashrc for login shells. */
934 no_rc++;
935
936 /* Execute /etc/profile and one of the personal login shell
937 initialization files. */
938 if (no_profile == 0)
939 {
940 maybe_execute_file (SYS_PROFILE, 1);
941
942 if (act_like_sh) /* sh */
943 maybe_execute_file ("~/.profile", 1);
944 else if ((maybe_execute_file ("~/.bash_profile", 1) == 0) &&
945 (maybe_execute_file ("~/.bash_login", 1) == 0)) /* bash */
946 maybe_execute_file ("~/.profile", 1);
947 }
948 }
949
950 /* bash */
951 if (act_like_sh == 0 && no_rc == 0)
952 {
953 #ifdef SYS_BASHRC
954 # if defined (__OPENNT)
955 maybe_execute_file (_prefixInstallPath(SYS_BASHRC, NULL, 0), 1);
956 # else
957 maybe_execute_file (SYS_BASHRC, 1);
958 # endif`
959 #endif
960 maybe_execute_file (bashrc_file, 1);
961 }
962 /* sh */
963 else if (act_like_sh && privileged_mode == 0 && sourced_env++ == 0)
964 execute_env_file (get_string_value ("ENV"));
965 }
966 else /* bash --posix, sh --posix */
967 {
968 /* bash and sh */
969 if (interactive_shell && privileged_mode == 0 && sourced_env++ == 0)
970 execute_env_file (get_string_value ("ENV"));
971 }
972
973 #if defined (JOB_CONTROL)
974 set_job_control (old_job_control);
975 #endif
976 }
977
978 #if defined (RESTRICTED_SHELL)
979 /* Return 1 if the shell should be a restricted one based on NAME or the
980 value of `restricted'. Don't actually do anything, just return a
981 boolean value. */
982 int
983 shell_is_restricted (name)
984 char *name;
985 {
986 char *temp;
987
988 if (restricted)
989 return 1;
990 temp = base_pathname (name);
991 return (STREQ (temp, RESTRICTED_SHELL_NAME));
992 }
993
994 /* Perhaps make this shell a `restricted' one, based on NAME. If the
995 basename of NAME is "rbash", then this shell is restricted. The
996 name of the restricted shell is a configurable option, see config.h.
997 In a restricted shell, PATH, SHELL, ENV, and BASH_ENV are read-only
998 and non-unsettable.
999 Do this also if `restricted' is already set to 1; maybe the shell was
1000 started with -r. */
1001 int
1002 maybe_make_restricted (name)
1003 char *name;
1004 {
1005 char *temp;
1006
1007 temp = base_pathname (shell_name);
1008 if (restricted || (STREQ (temp, RESTRICTED_SHELL_NAME)))
1009 {
1010 set_var_read_only ("PATH");
1011 set_var_read_only ("SHELL");
1012 set_var_read_only ("ENV");
1013 set_var_read_only ("BASH_ENV");
1014 restricted++;
1015 }
1016 return (restricted);
1017 }
1018 #endif /* RESTRICTED_SHELL */
1019
1020 /* Fetch the current set of uids and gids and return 1 if we're running
1021 setuid or setgid. */
1022 static int
1023 uidget ()
1024 {
1025 uid_t u;
1026
1027 u = getuid ();
1028 if (current_user.uid != u)
1029 {
1030 FREE (current_user.user_name);
1031 FREE (current_user.shell);
1032 FREE (current_user.home_dir);
1033 current_user.user_name = current_user.shell = current_user.home_dir = (char *)NULL;
1034 }
1035 current_user.uid = u;
1036 current_user.gid = getgid ();
1037 current_user.euid = geteuid ();
1038 current_user.egid = getegid ();
1039
1040 /* See whether or not we are running setuid or setgid. */
1041 return (current_user.uid != current_user.euid) ||
1042 (current_user.gid != current_user.egid);
1043 }
1044
1045 void
1046 disable_priv_mode ()
1047 {
1048 setuid (current_user.uid);
1049 setgid (current_user.gid);
1050 current_user.euid = current_user.uid;
1051 current_user.egid = current_user.gid;
1052 }
1053
1054 static int
1055 run_wordexp (words)
1056 char *words;
1057 {
1058 int code, nw, nb;
1059 WORD_DESC *w;
1060 WORD_LIST *wl, *result;
1061
1062 code = setjmp (top_level);
1063
1064 if (code != NOT_JUMPED)
1065 {
1066 switch (code)
1067 {
1068 /* Some kind of throw to top_level has occured. */
1069 case FORCE_EOF:
1070 return last_command_exit_value = 127;
1071 case EXITPROG:
1072 return last_command_exit_value;
1073 case DISCARD:
1074 return last_command_exit_value = 1;
1075 default:
1076 command_error ("run_wordexp", CMDERR_BADJUMP, code, 0);
1077 }
1078 }
1079
1080 /* Run it through the parser to get a list of words and expand them */
1081 if (words && *words)
1082 {
1083 with_input_from_string (words, "--wordexp");
1084 if (parse_command () != 0)
1085 return (126);
1086 if (global_command == 0)
1087 {
1088 printf ("0\n0\n");
1089 return (0);
1090 }
1091 if (global_command->type != cm_simple)
1092 return (126);
1093 wl = global_command->value.Simple->words;
1094 result = wl ? expand_words_no_vars (wl) : (WORD_LIST *)0;
1095 }
1096 else
1097 result = (WORD_LIST *)0;
1098
1099 last_command_exit_value = 0;
1100
1101 if (result == 0)
1102 {
1103 printf ("0\n0\n");
1104 return (0);
1105 }
1106
1107 /* Count up the number of words and bytes, and print them. Don't count
1108 the trailing NUL byte. */
1109 for (nw = nb = 0, wl = result; wl; wl = wl->next)
1110 {
1111 nw++;
1112 nb += strlen (wl->word->word);
1113 }
1114 printf ("%u\n%u\n", nw, nb);
1115 /* Print each word on a separate line. This will have to be changed when
1116 the interface to glibc is completed. */
1117 for (wl = result; wl; wl = wl->next)
1118 printf ("%s\n", wl->word->word);
1119
1120 return (0);
1121 }
1122
1123 #if defined (ONESHOT)
1124 /* Run one command, given as the argument to the -c option. Tell
1125 parse_and_execute not to fork for a simple command. */
1126 static int
1127 run_one_command (command)
1128 char *command;
1129 {
1130 int code;
1131
1132 code = setjmp (top_level);
1133
1134 if (code != NOT_JUMPED)
1135 {
1136 #if defined (PROCESS_SUBSTITUTION)
1137 unlink_fifo_list ();
1138 #endif /* PROCESS_SUBSTITUTION */
1139 switch (code)
1140 {
1141 /* Some kind of throw to top_level has occured. */
1142 case FORCE_EOF:
1143 return last_command_exit_value = 127;
1144 case EXITPROG:
1145 return last_command_exit_value;
1146 case DISCARD:
1147 return last_command_exit_value = 1;
1148 default:
1149 command_error ("run_one_command", CMDERR_BADJUMP, code, 0);
1150 }
1151 }
1152 return (parse_and_execute (savestring (command), "-c", SEVAL_NOHIST));
1153 }
1154 #endif /* ONESHOT */
1155
1156 static int
1157 bind_args (argv, arg_start, arg_end, start_index)
1158 char **argv;
1159 int arg_start, arg_end, start_index;
1160 {
1161 register int i;
1162 WORD_LIST *args;
1163
1164 for (i = arg_start, args = (WORD_LIST *)NULL; i != arg_end; i++)
1165 args = make_word_list (make_word (argv[i]), args);
1166 if (args)
1167 {
1168 args = REVERSE_LIST (args, WORD_LIST *);
1169 if (start_index == 0) /* bind to $0...$n for sh -c command */
1170 {
1171 /* Posix.2 4.56.3 says that the first argument after sh -c command
1172 becomes $0, and the rest of the arguments become $1...$n */
1173 shell_name = savestring (args->word->word);
1174 FREE (dollar_vars[0]);
1175 dollar_vars[0] = savestring (args->word->word);
1176 remember_args (args->next, 1);
1177 }
1178 else /* bind to $1...$n for shell script */
1179 remember_args (args, 1);
1180
1181 dispose_words (args);
1182 }
1183
1184 return (i);
1185 }
1186
1187 void
1188 unbind_args ()
1189 {
1190 remember_args ((WORD_LIST *)NULL, 1);
1191 }
1192
1193 static int
1194 open_shell_script (script_name)
1195 char *script_name;
1196 {
1197 int fd, e;
1198 char *filename, *path_filename;
1199 unsigned char sample[80];
1200 int sample_len;
1201 struct stat sb;
1202
1203 free (dollar_vars[0]);
1204 dollar_vars[0] = savestring (script_name);
1205 filename = savestring (script_name);
1206
1207 fd = open (filename, O_RDONLY);
1208 if ((fd < 0) && (errno == ENOENT) && (absolute_program (filename) == 0))
1209 {
1210 e = errno;
1211 /* If it's not in the current directory, try looking through PATH
1212 for it. */
1213 path_filename = find_path_file (script_name);
1214 if (path_filename)
1215 {
1216 free (filename);
1217 filename = path_filename;
1218 fd = open (filename, O_RDONLY);
1219 }
1220 else
1221 errno = e;
1222 }
1223
1224 if (fd < 0)
1225 {
1226 e = errno;
1227 file_error (filename);
1228 exit ((e == ENOENT) ? EX_NOTFOUND : EX_NOINPUT);
1229 }
1230
1231 /* Only do this with file descriptors we can seek on. */
1232 if (lseek (fd, 0L, 1) != -1)
1233 {
1234 /* Check to see if the `file' in `bash file' is a binary file
1235 according to the same tests done by execute_simple_command (),
1236 and report an error and exit if it is. */
1237 sample_len = read (fd, sample, sizeof (sample));
1238 if (sample_len < 0)
1239 {
1240 e = errno;
1241 if ((fstat (fd, &sb) == 0) && S_ISDIR (sb.st_mode))
1242 internal_error ("%s: is a directory", filename);
1243 else
1244 {
1245 errno = e;
1246 file_error (filename);
1247 }
1248 exit (EX_NOEXEC);
1249 }
1250 else if (sample_len > 0 && (check_binary_file (sample, sample_len)))
1251 {
1252 internal_error ("%s: cannot execute binary file", filename);
1253 exit (EX_BINARY_FILE);
1254 }
1255 /* Now rewind the file back to the beginning. */
1256 lseek (fd, 0L, 0);
1257 }
1258
1259 #if defined (BUFFERED_INPUT)
1260 default_buffered_input = fd;
1261 # if 0
1262 /* This is never executed. */
1263 if (default_buffered_input == -1)
1264 {
1265 file_error (filename);
1266 exit (EX_NOTFOUND);
1267 }
1268 # endif
1269 SET_CLOSE_ON_EXEC (default_buffered_input);
1270 #else /* !BUFFERED_INPUT */
1271 /* Open the script. But try to move the file descriptor to a randomly
1272 large one, in the hopes that any descriptors used by the script will
1273 not match with ours. */
1274 fd = move_to_high_fd (fd, 0, -1);
1275
1276 default_input = fdopen (fd, "r");
1277
1278 if (default_input == 0)
1279 {
1280 file_error (filename);
1281 exit (EX_NOTFOUND);
1282 }
1283
1284 SET_CLOSE_ON_EXEC (fd);
1285 if (fileno (default_input) != fd)
1286 SET_CLOSE_ON_EXEC (fileno (default_input));
1287 #endif /* !BUFFERED_INPUT */
1288
1289 if (interactive_shell == 0 || isatty (fd) == 0)
1290 /* XXX - does this really need to be called again here? */
1291 init_noninteractive ();
1292 else
1293 {
1294 /* I don't believe that this code is ever executed, even in
1295 the presence of /dev/fd. */
1296 dup2 (fd, 0);
1297 close (fd);
1298 fd = 0;
1299 #if defined (BUFFERED_INPUT)
1300 default_buffered_input = 0;
1301 #else
1302 fclose (default_input);
1303 default_input = stdin;
1304 #endif
1305 }
1306 free (filename);
1307 return (fd);
1308 }
1309
1310 /* Initialize the input routines for the parser. */
1311 static void
1312 set_bash_input ()
1313 {
1314 /* Make sure the fd from which we are reading input is not in
1315 no-delay mode. */
1316 #if defined (BUFFERED_INPUT)
1317 if (interactive == 0)
1318 unset_nodelay_mode (default_buffered_input);
1319 else
1320 #endif /* !BUFFERED_INPUT */
1321 unset_nodelay_mode (fileno (stdin));
1322
1323 /* with_input_from_stdin really means `with_input_from_readline' */
1324 if (interactive && no_line_editing == 0)
1325 with_input_from_stdin ();
1326 else
1327 #if defined (BUFFERED_INPUT)
1328 {
1329 if (interactive == 0)
1330 with_input_from_buffered_stream (default_buffered_input, dollar_vars[0]);
1331 else
1332 with_input_from_stream (default_input, dollar_vars[0]);
1333 }
1334 #else /* !BUFFERED_INPUT */
1335 with_input_from_stream (default_input, dollar_vars[0]);
1336 #endif /* !BUFFERED_INPUT */
1337 }
1338
1339 /* Close the current shell script input source and forget about it. This is
1340 extern so execute_cmd.c:initialize_subshell() can call it. If CHECK_ZERO
1341 is non-zero, we close default_buffered_input even if it's the standard
1342 input (fd 0). */
1343 void
1344 unset_bash_input (check_zero)
1345 int check_zero;
1346 {
1347 #if defined (BUFFERED_INPUT)
1348 if ((check_zero && default_buffered_input >= 0) ||
1349 (check_zero == 0 && default_buffered_input > 0))
1350 {
1351 close_buffered_fd (default_buffered_input);
1352 default_buffered_input = bash_input.location.buffered_fd = -1;
1353 }
1354 #else /* !BUFFERED_INPUT */
1355 if (default_input)
1356 {
1357 fclose (default_input);
1358 default_input = (FILE *)NULL;
1359 }
1360 #endif /* !BUFFERED_INPUT */
1361 }
1362
1363
1364 #if !defined (PROGRAM)
1365 # define PROGRAM "bash"
1366 #endif
1367
1368 static void
1369 set_shell_name (argv0)
1370 char *argv0;
1371 {
1372 /* Here's a hack. If the name of this shell is "sh", then don't do
1373 any startup files; just try to be more like /bin/sh. */
1374 shell_name = base_pathname (argv0);
1375 if (*shell_name == '-')
1376 shell_name++;
1377 if (shell_name[0] == 's' && shell_name[1] == 'h' && shell_name[2] == '\0')
1378 act_like_sh++;
1379 if (shell_name[0] == 's' && shell_name[1] == 'u' && shell_name[2] == '\0')
1380 su_shell++;
1381
1382 shell_name = argv0;
1383 FREE (dollar_vars[0]);
1384 dollar_vars[0] = savestring (shell_name);
1385
1386 if (*shell_name == '-')
1387 {
1388 shell_name++;
1389 login_shell++;
1390 }
1391
1392 /* A program may start an interactive shell with
1393 "execl ("/bin/bash", "-", NULL)".
1394 If so, default the name of this shell to our name. */
1395 if (!shell_name || !*shell_name || (shell_name[0] == '-' && !shell_name[1]))
1396 shell_name = PROGRAM;
1397 }
1398
1399 static void
1400 init_interactive ()
1401 {
1402 interactive_shell = startup_state = interactive = 1;
1403 expand_aliases = 1;
1404 }
1405
1406 static void
1407 init_noninteractive ()
1408 {
1409 #if defined (HISTORY)
1410 bash_history_reinit (0);
1411 #endif /* HISTORY */
1412 interactive_shell = startup_state = interactive = 0;
1413 expand_aliases = 0;
1414 no_line_editing = 1;
1415 #if defined (JOB_CONTROL)
1416 set_job_control (0);
1417 #endif /* JOB_CONTROL */
1418 }
1419
1420 void
1421 get_current_user_info ()
1422 {
1423 struct passwd *entry;
1424
1425 /* Don't fetch this more than once. */
1426 if (current_user.user_name == 0)
1427 {
1428 entry = getpwuid (current_user.uid);
1429 if (entry)
1430 {
1431 current_user.user_name = savestring (entry->pw_name);
1432 current_user.shell = (entry->pw_shell && entry->pw_shell[0])
1433 ? savestring (entry->pw_shell)
1434 : savestring ("/bin/sh");
1435 current_user.home_dir = savestring (entry->pw_dir);
1436 }
1437 else
1438 {
1439 current_user.user_name = savestring ("I have no name!");
1440 current_user.shell = savestring ("/bin/sh");
1441 current_user.home_dir = savestring ("/");
1442 }
1443 endpwent ();
1444 }
1445 }
1446
1447 /* Do whatever is necessary to initialize the shell.
1448 Put new initializations in here. */
1449 static void
1450 shell_initialize ()
1451 {
1452 char hostname[256];
1453
1454 /* Line buffer output for stderr and stdout. */
1455 if (shell_initialized == 0)
1456 {
1457 setlinebuf (stderr);
1458 setlinebuf (stdout);
1459 }
1460
1461 /* Sort the array of shell builtins so that the binary search in
1462 find_shell_builtin () works correctly. */
1463 initialize_shell_builtins ();
1464
1465 /* Initialize the trap signal handlers before installing our own
1466 signal handlers. traps.c:restore_original_signals () is responsible
1467 for restoring the original default signal handlers. That function
1468 is called when we make a new child. */
1469 initialize_traps ();
1470 initialize_signals ();
1471
1472 /* It's highly unlikely that this will change. */
1473 if (current_host_name == 0)
1474 {
1475 /* Initialize current_host_name. */
1476 if (gethostname (hostname, 255) < 0)
1477 current_host_name = "??host??";
1478 else
1479 current_host_name = savestring (hostname);
1480 }
1481
1482 /* Initialize the stuff in current_user that comes from the password
1483 file. We don't need to do this right away if the shell is not
1484 interactive. */
1485 if (interactive_shell)
1486 get_current_user_info ();
1487
1488 /* Initialize our interface to the tilde expander. */
1489 tilde_initialize ();
1490
1491 /* Initialize internal and environment variables. Don't import shell
1492 functions from the environment if we are running in privileged or
1493 restricted mode or if the shell is running setuid. */
1494 #if defined (RESTRICTED_SHELL)
1495 initialize_shell_variables (shell_environment, privileged_mode||restricted||running_setuid);
1496 #else
1497 initialize_shell_variables (shell_environment, privileged_mode||running_setuid);
1498 #endif
1499
1500 #if 0
1501 /* Initialize filename hash tables. */
1502 initialize_filename_hashing ();
1503 #endif
1504
1505 /* Initialize the data structures for storing and running jobs. */
1506 initialize_job_control (0);
1507
1508 /* Initialize input streams to null. */
1509 initialize_bash_input ();
1510
1511 /* Initialize the shell options. Don't import the shell options
1512 from the environment variable $SHELLOPTS if we are running in
1513 privileged or restricted mode or if the shell is running setuid. */
1514 #if defined (RESTRICTED_SHELL)
1515 initialize_shell_options (privileged_mode||restricted||running_setuid);
1516 #else
1517 initialize_shell_options (privileged_mode||running_setuid);
1518 #endif
1519 }
1520
1521 /* Function called by main () when it appears that the shell has already
1522 had some initialization performed. This is supposed to reset the world
1523 back to a pristine state, as if we had been exec'ed. */
1524 static void
1525 shell_reinitialize ()
1526 {
1527 /* The default shell prompts. */
1528 primary_prompt = PPROMPT;
1529 secondary_prompt = SPROMPT;
1530
1531 /* Things that get 1. */
1532 current_command_number = 1;
1533
1534 /* We have decided that the ~/.bashrc file should not be executed
1535 for the invocation of each shell script. If the variable $ENV
1536 (or $BASH_ENV) is set, its value is used as the name of a file
1537 to source. */
1538 no_rc = no_profile = 1;
1539
1540 /* Things that get 0. */
1541 login_shell = make_login_shell = interactive = executing = 0;
1542 debugging = do_version = line_number = last_command_exit_value = 0;
1543 forced_interactive = interactive_shell = subshell_environment = 0;
1544 expand_aliases = 0;
1545
1546 #if defined (HISTORY)
1547 bash_history_reinit (0);
1548 #endif /* HISTORY */
1549
1550 #if defined (RESTRICTED_SHELL)
1551 restricted = 0;
1552 #endif /* RESTRICTED_SHELL */
1553
1554 /* Ensure that the default startup file is used. (Except that we don't
1555 execute this file for reinitialized shells). */
1556 bashrc_file = "~/.bashrc";
1557
1558 /* Delete all variables and functions. They will be reinitialized when
1559 the environment is parsed. */
1560 delete_all_variables (shell_variables);
1561 delete_all_variables (shell_functions);
1562
1563 #if 0
1564 /* Pretend the PATH variable has changed. */
1565 flush_hashed_filenames ();
1566 #endif
1567 }
1568
1569 static void
1570 show_shell_usage (fp, extra)
1571 FILE *fp;
1572 int extra;
1573 {
1574 int i;
1575 char *set_opts, *s, *t;
1576
1577 if (extra)
1578 fprintf (fp, "GNU bash, version %s-(%s)\n", shell_version_string (), MACHTYPE);
1579 fprintf (fp, "Usage:\t%s [GNU long option] [option] ...\n\t%s [GNU long option] [option] script-file ...\n",
1580 shell_name, shell_name);
1581 fputs ("GNU long options:\n", fp);
1582 for (i = 0; long_args[i].name; i++)
1583 fprintf (fp, "\t--%s\n", long_args[i].name);
1584
1585 fputs ("Shell options:\n", fp);
1586 fputs ("\t-irsD or -c command\t\t(invocation only)\n", fp);
1587
1588 for (i = 0, set_opts = 0; shell_builtins[i].name; i++)
1589 if (STREQ (shell_builtins[i].name, "set"))
1590 set_opts = savestring (shell_builtins[i].short_doc);
1591 if (set_opts)
1592 {
1593 s = strchr (set_opts, '[');
1594 if (s == 0)
1595 s = set_opts;
1596 while (*++s == '-')
1597 ;
1598 t = strchr (s, ']');
1599 if (t)
1600 *t = '\0';
1601 fprintf (fp, "\t-%s or -o option\n", s);
1602 free (set_opts);
1603 }
1604
1605 if (extra)
1606 {
1607 fprintf (fp, "Type `%s -c \"help set\"' for more information about shell options.\n", shell_name);
1608 fprintf (fp, "Type `%s -c help' for more information about shell builtin commands.\n", shell_name);
1609 fprintf (fp, "Use the `bashbug' command to report bugs.\n");
1610 }
1611 }
1612
1613 /* The second and subsequent conditions must match those used to decide
1614 whether or not to call getpeername() in isnetconn(). */
1615 #if defined (HAVE_SYS_SOCKET_H) && defined (HAVE_GETPEERNAME) && !defined (SVR4_2)
1616 # include <sys/socket.h>
1617 #endif
1618
1619 /* Is FD a socket or network connection? */
1620 static int
1621 isnetconn (fd)
1622 int fd;
1623 {
1624 #if defined (HAVE_GETPEERNAME) && !defined (SVR4_2) && !defined (__BEOS__)
1625 int rv, l;
1626 struct sockaddr sa;
1627
1628 l = sizeof(sa);
1629 rv = getpeername(fd, &sa, &l);
1630 /* Solaris 2.5 getpeername() returns EINVAL if the fd is not a socket. */
1631 return ((rv < 0 && (errno == ENOTSOCK || errno == EINVAL)) ? 0 : 1);
1632 #else /* !HAVE_GETPEERNAME || SVR4_2 || __BEOS__ */
1633 # if defined (SVR4) || defined (SVR4_2)
1634 /* Sockets on SVR4 and SVR4.2 are character special (streams) devices. */
1635 struct stat sb;
1636
1637 if (isatty (fd))
1638 return (0);
1639 if (fstat (fd, &sb) < 0)
1640 return (0);
1641 # if defined (S_ISFIFO)
1642 if (S_ISFIFO (sb.st_mode))
1643 return (0);
1644 # endif /* S_ISFIFO */
1645 return (S_ISCHR (sb.st_mode));
1646 # else /* !SVR4 && !SVR4_2 */
1647 # if defined (S_ISSOCK) && !defined (__BEOS__)
1648 struct stat sb;
1649
1650 if (fstat (fd, &sb) < 0)
1651 return (0);
1652 return (S_ISSOCK (sb.st_mode));
1653 # else /* !S_ISSOCK || __BEOS__ */
1654 return (0);
1655 # endif /* !S_ISSOCK || __BEOS__ */
1656 # endif /* !SVR4 && !SVR4_2 */
1657 #endif /* !HAVE_GETPEERNAME || SVR4_2 || __BEOS__ */
1658 }