1 /* vi: set sw=4 ts=4: */
3 * lash -- the BusyBox Lame-Ass SHell
5 * Copyright (C) 1999,2000,2001 by Lineo, inc.
6 * Written by Erik Andersen <andersen@lineo.com>, <andersee@debian.org>
8 * Based in part on ladsh.c by Michael K. Johnson and Erik W. Troan, which is
9 * under the following liberal license: "We have placed this source code in the
10 * public domain. Use it in any project, free or commercial."
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 2 of the License, or
15 * (at your option) any later version.
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
20 * General Public License for more details.
22 * You should have received a copy of the GNU General Public License
23 * along with this program; if not, write to the Free Software
24 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
28 /* This shell's parsing engine is officially at a dead-end.
29 * Future work shell work should be done using hush.c
32 //For debugging/development on the shell only...
43 #include <sys/ioctl.h>
51 #ifdef BB_LOCALE_SUPPORT
56 #define expand_t glob_t
59 static const int MAX_READ = 128; /* size of input buffer for `read' builtin */
60 #define JOB_STATUS_FORMAT "[%d] %-22s %.40s\n"
63 enum redir_type { REDIRECT_INPUT, REDIRECT_OVERWRITE,
67 static const unsigned int DEFAULT_CONTEXT=0x1;
68 static const unsigned int IF_TRUE_CONTEXT=0x2;
69 static const unsigned int IF_FALSE_CONTEXT=0x4;
70 static const unsigned int THEN_EXP_CONTEXT=0x8;
71 static const unsigned int ELSE_EXP_CONTEXT=0x10;
75 struct job *head; /* head of list of running jobs */
76 struct job *fg; /* current foreground job */
80 enum redir_type type; /* type of redirection */
81 int fd; /* file descriptor being redirected */
82 char *filename; /* file to redirect fd to */
86 pid_t pid; /* 0 if exited */
87 char **argv; /* program name and arguments */
88 int num_redirects; /* elements in redirection array */
89 struct redir_struct *redirects; /* I/O redirects */
90 int is_stopped; /* is the program currently running? */
91 struct job *family; /* pointer back to the child's parent job */
95 int jobid; /* job number */
96 int num_progs; /* total number of programs in job */
97 int running_progs; /* number of programs running */
98 char *text; /* name of job */
99 char *cmdbuf; /* buffer various argv's point into */
100 pid_t pgrp; /* process group ID for the job */
101 struct child_prog *progs; /* array of programs in job */
102 struct job *next; /* to track background commands */
103 int stopped_progs; /* number of programs alive, but stopped */
104 unsigned int job_context; /* bitmask defining current context */
105 struct jobset *job_list;
108 struct built_in_command {
109 char *cmd; /* name */
110 char *descr; /* description */
111 int (*function) (struct child_prog *); /* function ptr */
116 struct close_me *next;
119 /* function prototypes for builtins */
120 static int builtin_cd(struct child_prog *cmd);
121 static int builtin_exec(struct child_prog *cmd);
122 static int builtin_exit(struct child_prog *cmd);
123 static int builtin_fg_bg(struct child_prog *cmd);
124 static int builtin_help(struct child_prog *cmd);
125 static int builtin_jobs(struct child_prog *dummy);
126 static int builtin_pwd(struct child_prog *dummy);
127 static int builtin_export(struct child_prog *cmd);
128 static int builtin_source(struct child_prog *cmd);
129 static int builtin_unset(struct child_prog *cmd);
130 static int builtin_read(struct child_prog *cmd);
133 /* function prototypes for shell stuff */
134 static void mark_open(int fd);
135 static void mark_closed(int fd);
136 static void close_all(void);
137 static void checkjobs(struct jobset *job_list);
138 static void remove_job(struct jobset *j_list, struct job *job);
139 static int get_command(FILE * source, char *command);
140 static int parse_command(char **command_ptr, struct job *job, int *inbg);
141 static int run_command(struct job *newjob, int inbg, int outpipe[2]);
142 static int pseudo_exec(struct child_prog *cmd) __attribute__ ((noreturn));
143 static int busy_loop(FILE * input);
146 /* Table of built-in functions (these are non-forking builtins, meaning they
147 * can change global variables in the parent shell process but they will not
148 * work with pipes and redirects; 'unset foo | whatever' will not work) */
149 static struct built_in_command bltins[] = {
150 {"bg", "Resume a job in the background", builtin_fg_bg},
151 {"cd", "Change working directory", builtin_cd},
152 {"exec", "Exec command, replacing this shell with the exec'd process", builtin_exec},
153 {"exit", "Exit from shell()", builtin_exit},
154 {"fg", "Bring job into the foreground", builtin_fg_bg},
155 {"jobs", "Lists the active jobs", builtin_jobs},
156 {"export", "Set environment variable", builtin_export},
157 {"unset", "Unset environment variable", builtin_unset},
158 {"read", "Input environment variable", builtin_read},
159 {".", "Source-in and run commands in a file", builtin_source},
160 /* to do: add ulimit */
164 /* Table of forking built-in functions (things that fork cannot change global
165 * variables in the parent process, such as the current working directory) */
166 static struct built_in_command bltins_forking[] = {
167 {"pwd", "Print current directory", builtin_pwd},
168 {"help", "List shell built-in commands", builtin_help},
173 static int shell_context; /* Type prompt trigger (PS1 or PS2) */
176 /* Globals that are static to this file */
177 static const char *cwd;
178 static char *local_pending_command = NULL;
179 static struct jobset job_list = { NULL, NULL };
182 static struct close_me *close_me_head;
183 static int last_return_code;
184 static int last_bg_pid;
185 static unsigned int last_jobid;
186 static int shell_terminal;
187 static pid_t shell_pgrp;
189 static char *PS2 = "> ";
193 static inline void debug_printf(const char *format, ...)
196 va_start(args, format);
197 vfprintf(stderr, format, args);
201 static inline void debug_printf(const char *format, ...) { }
205 Most builtins need access to the struct child_prog that has
206 their arguments, previously coded as cmd->progs[0]. That coding
207 can exhibit a bug, if the builtin is not the first command in
208 a pipeline: "echo foo | exec sort" will attempt to exec foo.
210 builtin previous use notes
211 ------ ----------------- ---------
213 exec cmd->progs[0] squashed bug: didn't look for applets or forking builtins
215 fg_bg cmd->progs[0], job_list->head, job_list->fg
224 I added "struct job *family;" to struct child_prog,
225 and switched API to builtin_foo(struct child_prog *child);
226 So cmd->text becomes child->family->text
227 cmd->job_context becomes child->family->job_context
228 cmd->progs[0] becomes *child
229 job_list becomes child->family->job_list
232 /* built-in 'cd <path>' handler */
233 static int builtin_cd(struct child_prog *child)
237 if (child->argv[1] == NULL)
238 newdir = getenv("HOME");
240 newdir = child->argv[1];
242 printf("cd: %s: %m\n", newdir);
245 cwd = xgetcwd((char *)cwd);
251 /* built-in 'exec' handler */
252 static int builtin_exec(struct child_prog *child)
254 if (child->argv[1] == NULL)
255 return EXIT_SUCCESS; /* Really? */
262 /* built-in 'exit' handler */
263 static int builtin_exit(struct child_prog *child)
265 if (child->argv[1] == NULL)
268 exit (atoi(child->argv[1]));
271 /* built-in 'fg' and 'bg' handler */
272 static int builtin_fg_bg(struct child_prog *child)
275 struct job *job=NULL;
277 /* If they gave us no args, assume they want the last backgrounded task */
278 if (!child->argv[1]) {
279 for (job = child->family->job_list->head; job; job = job->next) {
280 if (job->jobid == last_jobid) {
285 error_msg("%s: no current job", child->argv[0]);
289 if (sscanf(child->argv[1], "%%%d", &jobnum) != 1) {
290 error_msg("%s: bad argument '%s'", child->argv[0], child->argv[1]);
293 for (job = child->family->job_list->head; job; job = job->next) {
294 if (job->jobid == jobnum) {
299 error_msg("%s: %d: no such job", child->argv[0], jobnum);
304 if (*child->argv[0] == 'f') {
305 /* Put the job into the foreground. */
306 tcsetpgrp(shell_terminal, job->pgrp);
308 child->family->job_list->fg = job;
311 /* Restart the processes in the job */
312 for (i = 0; i < job->num_progs; i++)
313 job->progs[i].is_stopped = 0;
315 job->stopped_progs = 0;
317 if ( (i=kill(- job->pgrp, SIGCONT)) < 0) {
319 remove_job(&job_list, job);
321 perror_msg("kill (SIGCONT)");
328 /* built-in 'help' handler */
329 static int builtin_help(struct child_prog *dummy)
331 struct built_in_command *x;
333 printf("\nBuilt-in commands:\n");
334 printf("-------------------\n");
335 for (x = bltins; x->cmd; x++) {
338 printf("%s\t%s\n", x->cmd, x->descr);
340 for (x = bltins_forking; x->cmd; x++) {
343 printf("%s\t%s\n", x->cmd, x->descr);
349 /* built-in 'jobs' handler */
350 static int builtin_jobs(struct child_prog *child)
355 for (job = child->family->job_list->head; job; job = job->next) {
356 if (job->running_progs == job->stopped_progs)
357 status_string = "Stopped";
359 status_string = "Running";
361 printf(JOB_STATUS_FORMAT, job->jobid, status_string, job->text);
367 /* built-in 'pwd' handler */
368 static int builtin_pwd(struct child_prog *dummy)
370 cwd = xgetcwd((char *)cwd);
377 /* built-in 'export VAR=value' handler */
378 static int builtin_export(struct child_prog *child)
381 char *v = child->argv[1];
385 for (e = environ; *e; e++) {
392 fprintf(stderr, "export: %m\n");
393 #ifdef BB_FEATURE_SH_FANCY_PROMPT
394 if (strncmp(v, "PS1=", 4)==0)
398 #ifdef BB_LOCALE_SUPPORT
399 if(strncmp(v, "LC_ALL=", 7)==0)
400 setlocale(LC_ALL, getenv("LC_ALL"));
401 if(strncmp(v, "LC_CTYPE=", 9)==0)
402 setlocale(LC_CTYPE, getenv("LC_CTYPE"));
408 /* built-in 'read VAR' handler */
409 static int builtin_read(struct child_prog *child)
411 int res = 0, len, newlen;
413 char string[MAX_READ];
415 if (child->argv[1]) {
416 /* argument (VAR) given: put "VAR=" into buffer */
417 strcpy(string, child->argv[1]);
418 len = strlen(string);
421 fgets(&string[len], sizeof(string) - len, stdin); /* read string */
422 newlen = strlen(string);
424 string[--newlen] = '\0'; /* chomp trailing newline */
426 ** string should now contain "VAR=<value>"
427 ** copy it (putenv() won't do that, so we must make sure
428 ** the string resides in a static buffer!)
431 if((s = strdup(string)))
434 fprintf(stderr, "read: %m\n");
437 fgets(string, sizeof(string), stdin);
442 /* Built-in '.' handler (read-in and execute commands from file) */
443 static int builtin_source(struct child_prog *child)
449 if (child->argv[1] == NULL)
452 input = fopen(child->argv[1], "r");
454 printf( "Couldn't open file '%s'\n", child->argv[1]);
460 /* Now run the file */
461 status = busy_loop(input);
467 /* built-in 'unset VAR' handler */
468 static int builtin_unset(struct child_prog *child)
470 if (child->argv[1] == NULL) {
471 printf( "unset: parameter required.\n");
474 unsetenv(child->argv[1]);
478 static void mark_open(int fd)
480 struct close_me *new = xmalloc(sizeof(struct close_me));
482 new->next = close_me_head;
486 static void mark_closed(int fd)
488 struct close_me *tmp;
489 if (close_me_head == NULL || close_me_head->fd != fd)
490 error_msg_and_die("corrupt close_me");
492 close_me_head = close_me_head->next;
496 static void close_all()
498 struct close_me *c, *tmp;
499 for (c=close_me_head; c; c=tmp) {
504 close_me_head = NULL;
508 /* free up all memory from a job */
509 static void free_job(struct job *cmd)
514 for (i = 0; i < cmd->num_progs; i++) {
515 free(cmd->progs[i].argv);
516 if (cmd->progs[i].redirects)
517 free(cmd->progs[i].redirects);
525 keep = cmd->job_list;
526 memset(cmd, 0, sizeof(struct job));
527 cmd->job_list = keep;
530 /* remove a job from a jobset */
531 static void remove_job(struct jobset *j_list, struct job *job)
536 if (job == j_list->head) {
537 j_list->head = job->next;
539 prevjob = j_list->head;
540 while (prevjob->next != job)
541 prevjob = prevjob->next;
542 prevjob->next = job->next;
546 last_jobid = j_list->head->jobid;
553 /* Checks to see if any background processes have exited -- if they
554 have, figure out why and see if a job has completed */
555 static void checkjobs(struct jobset *j_list)
562 while ((childpid = waitpid(-1, &status, WNOHANG | WUNTRACED)) > 0) {
563 for (job = j_list->head; job; job = job->next) {
565 while (prognum < job->num_progs &&
566 job->progs[prognum].pid != childpid) prognum++;
567 if (prognum < job->num_progs)
571 /* This happens on backticked commands */
575 if (WIFEXITED(status) || WIFSIGNALED(status)) {
577 job->running_progs--;
578 job->progs[prognum].pid = 0;
580 if (!job->running_progs) {
581 printf(JOB_STATUS_FORMAT, job->jobid, "Done", job->text);
583 remove_job(j_list, job);
587 job->stopped_progs++;
588 job->progs[prognum].is_stopped = 1;
591 /* Printing this stuff is a pain, since it tends to
592 * overwrite the prompt an inconveinient moments. So
594 if (job->stopped_progs == job->num_progs) {
595 printf(JOB_STATUS_FORMAT, job->jobid, "Stopped",
602 if (childpid == -1 && errno != ECHILD)
603 perror_msg("waitpid");
606 /* squirrel != NULL means we squirrel away copies of stdin, stdout,
607 * and stderr if they are redirected. */
608 static int setup_redirects(struct child_prog *prog, int squirrel[])
613 struct redir_struct *redir = prog->redirects;
615 for (i = 0; i < prog->num_redirects; i++, redir++) {
616 switch (redir->type) {
620 case REDIRECT_OVERWRITE:
621 mode = O_WRONLY | O_CREAT | O_TRUNC;
623 case REDIRECT_APPEND:
624 mode = O_WRONLY | O_CREAT | O_APPEND;
628 openfd = open(redir->filename, mode, 0666);
630 /* this could get lost if stderr has been redirected, but
631 bash and ash both lose it as well (though zsh doesn't!) */
632 perror_msg("error opening %s", redir->filename);
636 if (openfd != redir->fd) {
637 if (squirrel && redir->fd < 3) {
638 squirrel[redir->fd] = dup(redir->fd);
640 dup2(openfd, redir->fd);
648 static void restore_redirects(int squirrel[])
651 for (i=0; i<3; i++) {
654 /* No error checking. I sure wouldn't know what
655 * to do with an error if I found one! */
662 static inline void cmdedit_set_initial_prompt(void)
664 #ifndef BB_FEATURE_SH_FANCY_PROMPT
673 static inline void setup_prompt_string(char **prompt_str)
675 #ifndef BB_FEATURE_SH_FANCY_PROMPT
676 /* Set up the prompt */
677 if (shell_context == 0) {
680 PS1=xmalloc(strlen(cwd)+4);
681 sprintf(PS1, "%s %s", cwd, ( geteuid() != 0 ) ? "$ ":"# ");
687 *prompt_str = (shell_context==0)? PS1 : PS2;
691 static int get_command(FILE * source, char *command)
695 if (source == NULL) {
696 if (local_pending_command) {
697 /* a command specified (-c option): return it & mark it done */
698 strcpy(command, local_pending_command);
699 free(local_pending_command);
700 local_pending_command = NULL;
706 if (source == stdin) {
707 setup_prompt_string(&prompt_str);
709 #ifdef BB_FEATURE_COMMAND_EDITING
711 ** enable command line editing only while a command line
712 ** is actually being read; otherwise, we'll end up bequeathing
713 ** atexit() handlers and other unwanted stuff to our
714 ** child processes (rob@sysgo.de)
716 cmdedit_read_input(prompt_str, command);
719 fputs(prompt_str, stdout);
723 if (!fgets(command, BUFSIZ - 2, source)) {
732 static char* itoa(register int i)
734 static char a[7]; /* Max 7 ints */
735 register char *b = a + sizeof(a) - 1;
743 *--b = '0' + (i % 10);
752 char * strsep_space( char *string, int * ix)
758 /* Short circuit the trivial case */
759 if ( !string || ! string[*ix])
762 /* Find the end of the token. */
763 while( string && string[*ix] && !isspace(string[*ix]) ) {
767 /* Find the end of any whitespace trailing behind
768 * the token and let that be part of the token */
769 while( string && string[*ix] && isspace(string[*ix]) ) {
773 if (! string && *ix==0) {
774 /* Nothing useful was found */
778 token = xmalloc(*ix+1);
780 strncpy(token, string, *ix);
785 static int expand_arguments(char *command)
787 int total_length=0, length, i, retval, ix = 0;
788 expand_t expand_result;
789 char *tmpcmd, *cmd, *cmd_copy;
790 char *src, *dst, *var;
791 const char *out_of_space = "out of space during expansion";
792 int flags = GLOB_NOCHECK
801 /* get rid of the terminating \n */
804 /* Fix up escape sequences to be the Real Thing(tm) */
805 while( command && command[ix]) {
806 if (command[ix] == '\\') {
807 const char *tmp = command+ix+1;
808 command[ix] = process_escape_sequence( &tmp );
809 memmove(command+ix + 1, tmp, strlen(tmp)+1);
813 /* Use glob and then fixup environment variables and such */
815 /* It turns out that glob is very stupid. We have to feed it one word at a
816 * time since it can't cope with a full string. Here we convert command
817 * (char*) into cmd (char**, one word per string) */
819 /* We need a clean copy, so strsep can mess up the copy while
820 * we write stuff into the original (in a minute) */
821 cmd = cmd_copy = strdup(command);
823 for (ix = 0, tmpcmd = cmd;
824 (tmpcmd = strsep_space(cmd, &ix)) != NULL; cmd += ix, ix=0) {
827 /* we need to trim() the result for glob! */
829 retval = glob(tmpcmd, flags, NULL, &expand_result);
830 free(tmpcmd); /* Free mem allocated by strsep_space */
831 if (retval == GLOB_NOSPACE) {
832 /* Mem may have been allocated... */
833 globfree (&expand_result);
834 error_msg(out_of_space);
836 } else if (retval != 0) {
837 /* Some other error. GLOB_NOMATCH shouldn't
838 * happen because of the GLOB_NOCHECK flag in
840 error_msg("syntax error");
843 /* Convert from char** (one word per string) to a simple char*,
844 * but don't overflow command which is BUFSIZ in length */
845 for (i=0; i < expand_result.gl_pathc; i++) {
846 length=strlen(expand_result.gl_pathv[i]);
847 if (total_length+length+1 >= BUFSIZ) {
848 error_msg(out_of_space);
851 strcat(command+total_length, " ");
853 strcat(command+total_length, expand_result.gl_pathv[i]);
854 total_length+=length;
856 globfree (&expand_result);
862 /* Now do the shell variable substitutions which
863 * wordexp can't do for us, namely $? and $! */
865 while((dst = strchr(src,'$')) != NULL){
869 var = itoa(last_return_code);
875 var = itoa(last_bg_pid);
877 /* Everything else like $$, $#, $[0-9], etc. should all be
878 * expanded by wordexp(), so we can in theory skip that stuff
879 * here, but just to be on the safe side (i.e., since uClibc
880 * wordexp doesn't do this stuff yet), lets leave it in for
883 var = itoa(getpid());
888 case '0':case '1':case '2':case '3':case '4':
889 case '5':case '6':case '7':case '8':case '9':
891 int ixx=*(dst + 1)-48;
902 /* a single character construction was found, and
903 * already handled in the case statement */
906 /* Looks like an environment variable */
908 int num_skip_chars=0;
909 int dstlen = strlen(dst);
910 /* Is this a ${foo} type variable? */
911 if (dstlen >=2 && *(dst+1) == '{') {
912 src=strchr(dst+1, '}');
916 while(isalnum(*src) || *src=='_') src++;
922 *src='\0'; /* temporary */
923 var = getenv(dst + 1 + num_skip_chars);
925 src += num_skip_chars;
928 /* Seems we got an un-expandable variable. So delete it. */
932 int subst_len = strlen(var);
933 int trail_len = strlen(src);
934 if (dst+subst_len+trail_len >= command+BUFSIZ) {
935 error_msg(out_of_space);
938 /* Move stuff to the end of the string to accommodate
939 * filling the created gap with the new stuff */
940 memmove(dst+subst_len, src, trail_len+1);
941 /* Now copy in the new stuff */
942 memcpy(dst, var, subst_len);
950 /* Return cmd->num_progs as 0 if no command is present (e.g. an empty
951 line). If a valid command is found, command_ptr is set to point to
952 the beginning of the next command (if the original command had more
953 then one job associated with it) or NULL if no more commands are
955 static int parse_command(char **command_ptr, struct job *job, int *inbg)
958 char *return_command = NULL;
959 char *src, *buf, *chptr;
963 int i, saw_quote = 0;
966 struct child_prog *prog;
968 /* skip leading white space */
969 while (**command_ptr && isspace(**command_ptr))
972 /* this handles empty lines or leading '#' characters */
973 if (!**command_ptr || (**command_ptr == '#')) {
980 job->progs = xmalloc(sizeof(*job->progs));
982 /* We set the argv elements to point inside of this string. The
983 memory is freed by free_job(). Allocate twice the original
984 length in case we need to quote every single character.
986 Getting clean memory relieves us of the task of NULL
987 terminating things and makes the rest of this look a bit
988 cleaner (though it is, admittedly, a tad less efficient) */
989 job->cmdbuf = command = xcalloc(2*strlen(*command_ptr) + 1, sizeof(char));
993 prog->num_redirects = 0;
994 prog->redirects = NULL;
995 prog->is_stopped = 0;
999 prog->argv = xmalloc(sizeof(*prog->argv) * argv_alloced);
1000 prog->argv[0] = job->cmdbuf;
1004 while (*src && !done) {
1005 if (quote == *src) {
1011 error_msg("character expected after \\");
1016 /* in shell, "\'" should yield \' */
1017 if (*src != quote) {
1021 } else if (*src == '*' || *src == '?' || *src == '[' ||
1022 *src == ']') *buf++ = '\\';
1024 } else if (isspace(*src)) {
1025 if (*prog->argv[argc_l] || saw_quote) {
1027 /* +1 here leaves room for the NULL which ends argv */
1028 if ((argc_l + 1) == argv_alloced) {
1030 prog->argv = xrealloc(prog->argv,
1031 sizeof(*prog->argv) *
1034 prog->argv[argc_l] = buf;
1045 case '#': /* comment */
1052 case '>': /* redirects */
1054 i = prog->num_redirects++;
1055 prog->redirects = xrealloc(prog->redirects,
1056 sizeof(*prog->redirects) *
1059 prog->redirects[i].fd = -1;
1060 if (buf != prog->argv[argc_l]) {
1061 /* the stuff before this character may be the file number
1063 prog->redirects[i].fd =
1064 strtol(prog->argv[argc_l], &chptr, 10);
1066 if (*chptr && *prog->argv[argc_l]) {
1068 prog->argv[argc_l] = buf;
1072 if (prog->redirects[i].fd == -1) {
1074 prog->redirects[i].fd = 1;
1076 prog->redirects[i].fd = 0;
1079 if (*src++ == '>') {
1081 prog->redirects[i].type =
1082 REDIRECT_APPEND, src++;
1084 prog->redirects[i].type = REDIRECT_OVERWRITE;
1086 prog->redirects[i].type = REDIRECT_INPUT;
1089 /* This isn't POSIX sh compliant. Oh well. */
1091 while (isspace(*chptr))
1095 error_msg("file name expected after %c", *(src-1));
1101 prog->redirects[i].filename = buf;
1102 while (*chptr && !isspace(*chptr))
1105 src = chptr - 1; /* we src++ later */
1106 prog->argv[argc_l] = ++buf;
1109 case '|': /* pipe */
1110 /* finish this command */
1111 if (*prog->argv[argc_l] || saw_quote)
1114 error_msg("empty command in pipe");
1119 prog->argv[argc_l] = NULL;
1121 /* and start the next */
1123 job->progs = xrealloc(job->progs,
1124 sizeof(*job->progs) * job->num_progs);
1125 prog = job->progs + (job->num_progs - 1);
1126 prog->num_redirects = 0;
1127 prog->redirects = NULL;
1128 prog->is_stopped = 0;
1133 prog->argv = xmalloc(sizeof(*prog->argv) * argv_alloced);
1134 prog->argv[0] = ++buf;
1137 while (*src && isspace(*src))
1141 error_msg("empty command in pipe");
1146 src--; /* we'll ++ it at the end of the loop */
1150 case '&': /* background */
1152 case ';': /* multiple commands */
1154 return_command = *command_ptr + (src - *command_ptr) + 1;
1160 error_msg("character expected after \\");
1164 if (*src == '*' || *src == '[' || *src == ']'
1165 || *src == '?') *buf++ = '\\';
1174 if (*prog->argv[argc_l] || saw_quote) {
1181 prog->argv[argc_l] = NULL;
1183 if (!return_command) {
1184 job->text = xmalloc(strlen(*command_ptr) + 1);
1185 strcpy(job->text, *command_ptr);
1187 /* This leaves any trailing spaces, which is a bit sloppy */
1188 count = return_command - *command_ptr;
1189 job->text = xmalloc(count + 1);
1190 strncpy(job->text, *command_ptr, count);
1191 job->text[count] = '\0';
1194 *command_ptr = return_command;
1199 /* Run the child_prog, no matter what kind of command it uses.
1201 static int pseudo_exec(struct child_prog *child)
1203 struct built_in_command *x;
1204 #ifdef BB_FEATURE_SH_STANDALONE_SHELL
1208 /* Check if the command matches any of the non-forking builtins.
1209 * Depending on context, this might be redundant. But it's
1210 * easier to waste a few CPU cycles than it is to figure out
1211 * if this is one of those cases.
1213 for (x = bltins; x->cmd; x++) {
1214 if (strcmp(child->argv[0], x->cmd) == 0 ) {
1215 exit(x->function(child));
1219 /* Check if the command matches any of the forking builtins. */
1220 for (x = bltins_forking; x->cmd; x++) {
1221 if (strcmp(child->argv[0], x->cmd) == 0) {
1223 exit (x->function(child));
1226 #ifdef BB_FEATURE_SH_STANDALONE_SHELL
1227 /* Check if the command matches any busybox internal
1228 * commands ("applets") here. Following discussions from
1229 * November 2000 on busybox@opensource.lineo.com, don't use
1230 * get_last_path_component(). This way explicit (with
1231 * slashes) filenames will never be interpreted as an
1232 * applet, just like with builtins. This way the user can
1233 * override an applet with an explicit filename reference.
1234 * The only downside to this change is that an explicit
1235 * /bin/foo invocation will fork and exec /bin/foo, even if
1236 * /bin/foo is a symlink to busybox.
1238 name = child->argv[0];
1240 #ifdef BB_FEATURE_SH_APPLETS_ALWAYS_WIN
1241 /* If you enable BB_FEATURE_SH_APPLETS_ALWAYS_WIN, then
1242 * if you run /bin/cat, it will use BusyBox cat even if
1243 * /bin/cat exists on the filesystem and is _not_ busybox.
1244 * Some systems want this, others do not. Choose wisely. :-)
1246 name = get_last_path_component(name);
1250 char** argv_l=child->argv;
1252 for(argc_l=0;*argv_l!=NULL; argv_l++, argc_l++);
1254 run_applet_by_name(name, argc_l, child->argv);
1258 execvp(child->argv[0], child->argv);
1259 perror_msg_and_die("%s", child->argv[0]);
1262 static void insert_job(struct job *newjob, int inbg)
1265 struct jobset *j_list=newjob->job_list;
1267 /* find the ID for thejob to use */
1269 for (thejob = j_list->head; thejob; thejob = thejob->next)
1270 if (thejob->jobid >= newjob->jobid)
1271 newjob->jobid = thejob->jobid + 1;
1273 /* add thejob to the list of running jobs */
1274 if (!j_list->head) {
1275 thejob = j_list->head = xmalloc(sizeof(*thejob));
1277 for (thejob = j_list->head; thejob->next; thejob = thejob->next) /* nothing */;
1278 thejob->next = xmalloc(sizeof(*thejob));
1279 thejob = thejob->next;
1282 *thejob = *newjob; /* physically copy the struct job */
1283 thejob->next = NULL;
1284 thejob->running_progs = thejob->num_progs;
1285 thejob->stopped_progs = 0;
1288 /* we don't wait for background thejobs to return -- append it
1289 to the list of backgrounded thejobs and leave it alone */
1290 printf("[%d] %d\n", thejob->jobid,
1291 newjob->progs[newjob->num_progs - 1].pid);
1292 last_jobid = newjob->jobid;
1293 last_bg_pid=newjob->progs[newjob->num_progs - 1].pid;
1295 newjob->job_list->fg = thejob;
1297 /* move the new process group into the foreground */
1298 /* suppress messages when run from /linuxrc mag@sysgo.de */
1299 if (tcsetpgrp(shell_terminal, newjob->pgrp) && errno != ENOTTY)
1300 perror_msg("tcsetpgrp");
1304 static int run_command(struct job *newjob, int inbg, int outpipe[2])
1306 /* struct job *thejob; */
1308 int nextin, nextout;
1309 int pipefds[2]; /* pipefd[0] is for reading */
1310 struct built_in_command *x;
1311 struct child_prog *child;
1313 nextin = 0, nextout = 1;
1314 for (i = 0; i < newjob->num_progs; i++) {
1315 child = & (newjob->progs[i]);
1317 if ((i + 1) < newjob->num_progs) {
1318 if (pipe(pipefds)<0) perror_msg_and_die("pipe");
1319 nextout = pipefds[1];
1321 if (outpipe[1]!=-1) {
1322 nextout = outpipe[1];
1329 /* Check if the command matches any non-forking builtins,
1330 * but only if this is a simple command.
1331 * Non-forking builtins within pipes have to fork anyway,
1332 * and are handled in pseudo_exec. "echo foo | read bar"
1333 * is doomed to failure, and doesn't work on bash, either.
1335 if (newjob->num_progs == 1) {
1336 for (x = bltins; x->cmd; x++) {
1337 if (strcmp(child->argv[0], x->cmd) == 0 ) {
1338 int squirrel[] = {-1, -1, -1};
1340 setup_redirects(child, squirrel);
1341 rcode = x->function(child);
1342 restore_redirects(squirrel);
1348 if (!(child->pid = fork())) {
1349 /* Set the handling for job control signals back to the default. */
1350 signal(SIGINT, SIG_DFL);
1351 signal(SIGQUIT, SIG_DFL);
1352 signal(SIGTSTP, SIG_DFL);
1353 signal(SIGTTIN, SIG_DFL);
1354 signal(SIGTTOU, SIG_DFL);
1355 signal(SIGCHLD, SIG_DFL);
1359 if (outpipe[1]!=-1) {
1369 dup2(nextout, 2); /* Really? */
1374 /* explicit redirects override pipes */
1375 setup_redirects(child,NULL);
1379 if (outpipe[1]!=-1) {
1383 /* put our child in the process group whose leader is the
1384 first process in this pipe */
1385 setpgid(child->pid, newjob->progs[0].pid);
1391 /* If there isn't another process, nextin is garbage
1392 but it doesn't matter */
1393 nextin = pipefds[0];
1396 newjob->pgrp = newjob->progs[0].pid;
1398 insert_job(newjob, inbg);
1403 static int busy_loop(FILE * input)
1406 char *next_command = NULL;
1412 newjob.job_list = &job_list;
1413 newjob.job_context = DEFAULT_CONTEXT;
1415 /* save current owner of TTY so we can restore it on exit */
1416 parent_pgrp = tcgetpgrp(shell_terminal);
1418 command = (char *) xcalloc(BUFSIZ, sizeof(char));
1422 /* no job is in the foreground */
1424 /* see if any background processes have exited */
1425 checkjobs(&job_list);
1427 if (!next_command) {
1428 if (get_command(input, command))
1430 next_command = command;
1433 if (expand_arguments(next_command) == FALSE) {
1435 command = (char *) xcalloc(BUFSIZ, sizeof(char));
1436 next_command = NULL;
1440 if (!parse_command(&next_command, &newjob, &inbg) &&
1442 int pipefds[2] = {-1,-1};
1443 debug_printf( "job=%p fed to run_command by busy_loop()'\n",
1445 run_command(&newjob, inbg, pipefds);
1449 command = (char *) xcalloc(BUFSIZ, sizeof(char));
1450 next_command = NULL;
1453 /* a job is running in the foreground; wait for it */
1455 while (!job_list.fg->progs[i].pid ||
1456 job_list.fg->progs[i].is_stopped == 1) i++;
1458 if (waitpid(job_list.fg->progs[i].pid, &status, WUNTRACED)<0)
1459 perror_msg_and_die("waitpid(%d)",job_list.fg->progs[i].pid);
1461 if (WIFEXITED(status) || WIFSIGNALED(status)) {
1462 /* the child exited */
1463 job_list.fg->running_progs--;
1464 job_list.fg->progs[i].pid = 0;
1466 last_return_code=WEXITSTATUS(status);
1468 if (!job_list.fg->running_progs) {
1470 remove_job(&job_list, job_list.fg);
1474 /* the child was stopped */
1475 job_list.fg->stopped_progs++;
1476 job_list.fg->progs[i].is_stopped = 1;
1478 if (job_list.fg->stopped_progs == job_list.fg->running_progs) {
1479 printf("\n" JOB_STATUS_FORMAT, job_list.fg->jobid,
1480 "Stopped", job_list.fg->text);
1486 /* move the shell to the foreground */
1487 /* suppress messages when run from /linuxrc mag@sysgo.de */
1488 if (tcsetpgrp(shell_terminal, getpgrp()) && errno != ENOTTY)
1489 perror_msg("tcsetpgrp");
1495 /* return controlling TTY back to parent process group before exiting */
1496 if (tcsetpgrp(shell_terminal, parent_pgrp))
1497 perror_msg("tcsetpgrp");
1499 /* return exit status if called with "-c" */
1500 if (input == NULL && WIFEXITED(status))
1501 return WEXITSTATUS(status);
1507 #ifdef BB_FEATURE_CLEAN_UP
1508 void free_memory(void)
1513 if (local_pending_command)
1514 free(local_pending_command);
1516 if (job_list.fg && !job_list.fg->running_progs) {
1517 remove_job(&job_list, job_list.fg);
1522 /* Make sure we have a controlling tty. If we get started under a job
1523 * aware app (like bash for example), make sure we are now in charge so
1524 * we don't fight over who gets the foreground */
1525 static void setup_job_control()
1527 /* Loop until we are in the foreground. */
1528 while (tcgetpgrp (shell_terminal) != (shell_pgrp = getpgrp ()))
1529 kill (- shell_pgrp, SIGTTIN);
1531 /* Ignore interactive and job-control signals. */
1532 signal(SIGINT, SIG_IGN);
1533 signal(SIGQUIT, SIG_IGN);
1534 signal(SIGTSTP, SIG_IGN);
1535 signal(SIGTTIN, SIG_IGN);
1536 signal(SIGTTOU, SIG_IGN);
1537 signal(SIGCHLD, SIG_IGN);
1539 /* Put ourselves in our own process group. */
1541 shell_pgrp = getpid ();
1542 setpgid (shell_pgrp, shell_pgrp);
1544 /* Grab control of the terminal. */
1545 tcsetpgrp(shell_terminal, shell_pgrp);
1548 int lash_main(int argc_l, char **argv_l)
1550 int opt, interactive=FALSE;
1551 FILE *input = stdin;
1555 /* These variables need re-initializing when recursing */
1557 local_pending_command = NULL;
1558 close_me_head = NULL;
1559 job_list.head = NULL;
1563 if (argv[0] && argv[0][0] == '-') {
1565 prof_input = fopen("/etc/profile", "r");
1567 int tmp_fd = fileno(prof_input);
1569 /* Now run the file */
1570 busy_loop(prof_input);
1572 mark_closed(tmp_fd);
1576 while ((opt = getopt(argc_l, argv_l, "cxi")) > 0) {
1580 if (local_pending_command != 0)
1581 error_msg_and_die("multiple -c arguments");
1582 local_pending_command = xstrdup(argv[optind]);
1593 /* A shell is interactive if the `-i' flag was given, or if all of
1594 * the following conditions are met:
1596 * no arguments remaining or the -s flag given
1597 * standard input is a terminal
1598 * standard output is a terminal
1599 * Refer to Posix.2, the description of the `sh' utility. */
1600 if (argv[optind]==NULL && input==stdin &&
1601 isatty(fileno(stdin)) && isatty(fileno(stdout))) {
1604 setup_job_control();
1605 if (interactive==TRUE) {
1606 //printf( "optind=%d argv[optind]='%s'\n", optind, argv[optind]);
1607 /* Looks like they want an interactive shell */
1608 printf( "\n\n" BB_BANNER " Built-in shell (lash)\n");
1609 printf( "Enter 'help' for a list of built-in commands.\n\n");
1610 } else if (local_pending_command==NULL) {
1611 //printf( "optind=%d argv[optind]='%s'\n", optind, argv[optind]);
1612 input = xfopen(argv[optind], "r");
1613 mark_open(fileno(input)); /* be lazy, never mark this closed */
1616 /* initialize the cwd -- this is never freed...*/
1621 #ifdef BB_FEATURE_CLEAN_UP
1622 atexit(free_memory);
1625 #ifdef BB_FEATURE_COMMAND_EDITING
1626 cmdedit_set_initial_prompt();
1631 return (busy_loop(input));