aboutsummaryrefslogtreecommitdiff
path: root/shell/hush.c
diff options
context:
space:
mode:
authorDenis Vlasenko <vda.linux@googlemail.com>2008-07-14 06:29:38 +0000
committerDenis Vlasenko <vda.linux@googlemail.com>2008-07-14 06:29:38 +0000
commit395ae452165a607c6b5bc4623225516044619616 (patch)
tree00ceff4dcd3fc4604d9252003cf45dfb6cfbedc1 /shell/hush.c
parent17f02e79f407ff2311255981c191a1bf8b3a7ae0 (diff)
downloadbusybox-w32-395ae452165a607c6b5bc4623225516044619616.tar.gz
busybox-w32-395ae452165a607c6b5bc4623225516044619616.tar.bz2
busybox-w32-395ae452165a607c6b5bc4623225516044619616.zip
hush: delete unused field in struct child.
reinstate needed check for invalid syntax. document command parsing in hush_doc.txt.
Diffstat (limited to 'shell/hush.c')
-rw-r--r--shell/hush.c34
1 files changed, 18 insertions, 16 deletions
diff --git a/shell/hush.c b/shell/hush.c
index 47e53f8c1..db608018c 100644
--- a/shell/hush.c
+++ b/shell/hush.c
@@ -322,7 +322,6 @@ struct child_prog {
322 char **argv; /* program name and arguments */ 322 char **argv; /* program name and arguments */
323 struct pipe *group; /* if non-NULL, first in group or subshell */ 323 struct pipe *group; /* if non-NULL, first in group or subshell */
324 struct redir_struct *redirects; /* I/O redirections */ 324 struct redir_struct *redirects; /* I/O redirections */
325 struct pipe *family; /* pointer back to the child's parent pipe */
326}; 325};
327/* argv vector may contain variable references (^Cvar^C, ^C0^C etc) 326/* argv vector may contain variable references (^Cvar^C, ^C0^C etc)
328 * and on execution these are substituted with their values. 327 * and on execution these are substituted with their values.
@@ -2830,7 +2829,6 @@ static void initialize_context(struct p_context *ctx)
2830 ctx->pipe = ctx->list_head = new_pipe(); 2829 ctx->pipe = ctx->list_head = new_pipe();
2831 /* Create the memory for child, roughly: 2830 /* Create the memory for child, roughly:
2832 * ctx->pipe->progs = new struct child_prog; 2831 * ctx->pipe->progs = new struct child_prog;
2833 * ctx->pipe->progs[0].family = ctx->pipe;
2834 * ctx->child = &ctx->pipe->progs[0]; 2832 * ctx->child = &ctx->pipe->progs[0];
2835 */ 2833 */
2836 done_command(ctx); 2834 done_command(ctx);
@@ -2960,6 +2958,7 @@ static int done_word(o_string *word, struct p_context *ctx)
2960{ 2958{
2961 struct child_prog *child = ctx->child; 2959 struct child_prog *child = ctx->child;
2962 2960
2961 debug_printf_parse("done_word entered: '%s' %p\n", word->data, child);
2963 /* If this word wasn't an assignment, next ones definitely 2962 /* If this word wasn't an assignment, next ones definitely
2964 * can't be assignments. Even if they look like ones. */ 2963 * can't be assignments. Even if they look like ones. */
2965 if (word->o_assignment != DEFINITELY_ASSIGNMENT) { 2964 if (word->o_assignment != DEFINITELY_ASSIGNMENT) {
@@ -2967,8 +2966,6 @@ static int done_word(o_string *word, struct p_context *ctx)
2967 } else { 2966 } else {
2968 word->o_assignment = MAYBE_ASSIGNMENT; 2967 word->o_assignment = MAYBE_ASSIGNMENT;
2969 } 2968 }
2970
2971 debug_printf_parse("done_word entered: '%s' %p\n", word->data, child);
2972 if (word->length == 0 && word->nonnull == 0) { 2969 if (word->length == 0 && word->nonnull == 0) {
2973 debug_printf_parse("done_word return 0: true null, ignored\n"); 2970 debug_printf_parse("done_word return 0: true null, ignored\n");
2974 return 0; 2971 return 0;
@@ -2980,15 +2977,17 @@ static int done_word(o_string *word, struct p_context *ctx)
2980 word->o_assignment = NOT_ASSIGNMENT; 2977 word->o_assignment = NOT_ASSIGNMENT;
2981 debug_printf("word stored in rd_filename: '%s'\n", word->data); 2978 debug_printf("word stored in rd_filename: '%s'\n", word->data);
2982 } else { 2979 } else {
2983// if (child->group) { /* TODO: example how to trigger? */ 2980 /* "{ echo foo; } echo bar" - bad */
2984// syntax(NULL); 2981 /* NB: bash allows e.g. "if true; then { echo foo; } fi". TODO? */
2985// debug_printf_parse("done_word return 1: syntax error, groups and arglists don't mix\n"); 2982 if (child->group) {
2986// return 1; 2983 syntax(NULL);
2987// } 2984 debug_printf_parse("done_word return 1: syntax error, groups and arglists don't mix\n");
2985 return 1;
2986 }
2988#if HAS_KEYWORDS 2987#if HAS_KEYWORDS
2989#if ENABLE_HUSH_CASE 2988#if ENABLE_HUSH_CASE
2990 if (ctx->ctx_dsemicolon) { 2989 if (ctx->ctx_dsemicolon) {
2991 /* already done when ctx_dsemicolon was set to 1 */ 2990 /* already done when ctx_dsemicolon was set to 1: */
2992 /* ctx->ctx_res_w = RES_MATCH; */ 2991 /* ctx->ctx_res_w = RES_MATCH; */
2993 ctx->ctx_dsemicolon = 0; 2992 ctx->ctx_dsemicolon = 0;
2994 } else 2993 } else
@@ -3085,9 +3084,7 @@ static int done_command(struct p_context *ctx)
3085 * child structure is not counted in pi->num_progs. */ 3084 * child structure is not counted in pi->num_progs. */
3086 pi->progs = xrealloc(pi->progs, sizeof(*pi->progs) * (pi->num_progs+1)); 3085 pi->progs = xrealloc(pi->progs, sizeof(*pi->progs) * (pi->num_progs+1));
3087 child = &pi->progs[pi->num_progs]; 3086 child = &pi->progs[pi->num_progs];
3088
3089 memset(child, 0, sizeof(*child)); 3087 memset(child, 0, sizeof(*child));
3090 child->family = pi;
3091 3088
3092 ctx->child = child; 3089 ctx->child = child;
3093 /* but ctx->pipe and ctx->list_head remain unchanged */ 3090 /* but ctx->pipe and ctx->list_head remain unchanged */
@@ -3100,22 +3097,28 @@ static void done_pipe(struct p_context *ctx, pipe_style type)
3100 int not_null; 3097 int not_null;
3101 3098
3102 debug_printf_parse("done_pipe entered, followup %d\n", type); 3099 debug_printf_parse("done_pipe entered, followup %d\n", type);
3103 not_null = done_command(ctx); /* implicit closure of previous command */ 3100 /* Close previous command */
3101 not_null = done_command(ctx);
3104 ctx->pipe->followup = type; 3102 ctx->pipe->followup = type;
3105 IF_HAS_KEYWORDS(ctx->pipe->pi_inverted = ctx->ctx_inverted;) 3103 IF_HAS_KEYWORDS(ctx->pipe->pi_inverted = ctx->ctx_inverted;)
3106 IF_HAS_KEYWORDS(ctx->ctx_inverted = 0;) 3104 IF_HAS_KEYWORDS(ctx->ctx_inverted = 0;)
3107 IF_HAS_KEYWORDS(ctx->pipe->res_word = ctx->ctx_res_w;) 3105 IF_HAS_KEYWORDS(ctx->pipe->res_word = ctx->ctx_res_w;)
3106
3108 /* Without this check, even just <enter> on command line generates 3107 /* Without this check, even just <enter> on command line generates
3109 * tree of three NOPs (!). Which is harmless but annoying. 3108 * tree of three NOPs (!). Which is harmless but annoying.
3110 * IOW: it is safe to do it unconditionally. 3109 * IOW: it is safe to do it unconditionally.
3111 * RES_NONE case is for "for a in; do ..." (empty IN set) 3110 * RES_NONE case is for "for a in; do ..." (empty IN set)
3112 * to work, possibly other cases too. */ 3111 * to work, possibly other cases too. */
3113 if (not_null IF_HAS_KEYWORDS(|| ctx->ctx_res_w != RES_NONE)) { 3112 if (not_null IF_HAS_KEYWORDS(|| ctx->ctx_res_w != RES_NONE)) {
3114 struct pipe *new_p = new_pipe(); 3113 struct pipe *new_p;
3114 debug_printf_parse("done_pipe: adding new pipe: "
3115 " not_null:%d ctx->ctx_res_w:%d\n",
3116 not_null, ctx->ctx_res_w);
3117 new_p = new_pipe();
3115 ctx->pipe->next = new_p; 3118 ctx->pipe->next = new_p;
3116 ctx->pipe = new_p; 3119 ctx->pipe = new_p;
3117 ctx->child = NULL; /* needed! */ 3120 ctx->child = NULL; /* needed! */
3118 /* RES_IF, RES_WHILE etc are "sticky" - 3121 /* RES_THEN, RES_DO etc are "sticky" -
3119 * they remain set for commands inside if/while. 3122 * they remain set for commands inside if/while.
3120 * This is used to control execution. 3123 * This is used to control execution.
3121 * RES_FOR and RES_IN are NOT sticky (needed to support 3124 * RES_FOR and RES_IN are NOT sticky (needed to support
@@ -3132,7 +3135,6 @@ static void done_pipe(struct p_context *ctx, pipe_style type)
3132#endif 3135#endif
3133 /* Create the memory for child, roughly: 3136 /* Create the memory for child, roughly:
3134 * ctx->pipe->progs = new struct child_prog; 3137 * ctx->pipe->progs = new struct child_prog;
3135 * ctx->pipe->progs[0].family = ctx->pipe;
3136 * ctx->child = &ctx->pipe->progs[0]; 3138 * ctx->child = &ctx->pipe->progs[0];
3137 */ 3139 */
3138 done_command(ctx); 3140 done_command(ctx);