aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--shell/hush.c15
-rw-r--r--shell/hush_test/hush-psubst/falsetick.right27
-rwxr-xr-xshell/hush_test/hush-psubst/falsetick.tests22
3 files changed, 59 insertions, 5 deletions
diff --git a/shell/hush.c b/shell/hush.c
index df81eaae7..8da9439c1 100644
--- a/shell/hush.c
+++ b/shell/hush.c
@@ -2523,7 +2523,7 @@ static NOINLINE int expand_vars_to_list(o_string *output, int n, char *arg, char
2523 * and $IFS-splitted */ 2523 * and $IFS-splitted */
2524 debug_printf_subst("SUBST '%s' first_ch %x\n", arg, first_ch); 2524 debug_printf_subst("SUBST '%s' first_ch %x\n", arg, first_ch);
2525 G.last_exitcode = process_command_subs(&subst_result, arg); 2525 G.last_exitcode = process_command_subs(&subst_result, arg);
2526 debug_printf_subst("SUBST RES '%s'\n", subst_result.data); 2526 debug_printf_subst("SUBST RES:%d '%s'\n", G.last_exitcode, subst_result.data);
2527 val = subst_result.data; 2527 val = subst_result.data;
2528 goto store_val; 2528 goto store_val;
2529#endif 2529#endif
@@ -4117,9 +4117,9 @@ static NOINLINE int run_pipe(struct pipe *pi)
4117 4117
4118 if (argv[command->assignment_cnt] == NULL) { 4118 if (argv[command->assignment_cnt] == NULL) {
4119 /* Assignments, but no command */ 4119 /* Assignments, but no command */
4120 /* Ensure redirects take effect. Try "a=t >file" */ 4120 /* Ensure redirects take effect (that is, create files).
4121 * Try "a=t >file": */
4121 rcode = setup_redirects(command, squirrel); 4122 rcode = setup_redirects(command, squirrel);
4122//FIXME: "false; q=`false`; echo $?" should print 1
4123 restore_redirects(squirrel); 4123 restore_redirects(squirrel);
4124 /* Set shell variables */ 4124 /* Set shell variables */
4125 while (*argv) { 4125 while (*argv) {
@@ -4129,6 +4129,11 @@ static NOINLINE int run_pipe(struct pipe *pi)
4129 set_local_var(p, /*exp:*/ 0, /*lvl:*/ 0, /*ro:*/ 0); 4129 set_local_var(p, /*exp:*/ 0, /*lvl:*/ 0, /*ro:*/ 0);
4130 argv++; 4130 argv++;
4131 } 4131 }
4132 /* Redirect error sets $? to 1. Othervise,
4133 * if evaluating assignment value set $?, retain it.
4134 * Try "false; q=`exit 2`; echo $?" - should print 2: */
4135 if (rcode == 0)
4136 rcode = G.last_exitcode;
4132 /* Do we need to flag set_local_var() errors? 4137 /* Do we need to flag set_local_var() errors?
4133 * "assignment to readonly var" and "putenv error" 4138 * "assignment to readonly var" and "putenv error"
4134 */ 4139 */
@@ -4186,7 +4191,7 @@ static NOINLINE int run_pipe(struct pipe *pi)
4186 old_vars = set_vars_and_save_old(new_env); 4191 old_vars = set_vars_and_save_old(new_env);
4187 if (!funcp) { 4192 if (!funcp) {
4188 debug_printf_exec(": builtin '%s' '%s'...\n", 4193 debug_printf_exec(": builtin '%s' '%s'...\n",
4189 x->cmd, argv_expanded[1]); 4194 x->b_cmd, argv_expanded[1]);
4190 rcode = x->b_function(argv_expanded) & 0xff; 4195 rcode = x->b_function(argv_expanded) & 0xff;
4191 fflush_all(); 4196 fflush_all();
4192 } 4197 }
@@ -6814,7 +6819,7 @@ int hush_main(int argc, char **argv)
6814 struct variable *cur_var; 6819 struct variable *cur_var;
6815 6820
6816 INIT_G(); 6821 INIT_G();
6817 if (EXIT_SUCCESS) /* if EXIT_SUCCESS == 0, is already done */ 6822 if (EXIT_SUCCESS) /* if EXIT_SUCCESS == 0, it is already done */
6818 G.last_exitcode = EXIT_SUCCESS; 6823 G.last_exitcode = EXIT_SUCCESS;
6819#if !BB_MMU 6824#if !BB_MMU
6820 G.argv0_for_re_execing = argv[0]; 6825 G.argv0_for_re_execing = argv[0];
diff --git a/shell/hush_test/hush-psubst/falsetick.right b/shell/hush_test/hush-psubst/falsetick.right
new file mode 100644
index 000000000..0b98fb778
--- /dev/null
+++ b/shell/hush_test/hush-psubst/falsetick.right
@@ -0,0 +1,27 @@
10
20
30
40
52
62
72
82
9hush: can't open '/does/not/exist': No such file or directory
101
11hush: can't open '/does/not/exist': No such file or directory
121
13hush: can't open '/does/not/exist': No such file or directory
141
15hush: can't open '/does/not/exist': No such file or directory
161
17hush: can't open '/does/not/exist': No such file or directory
181
19hush: can't open '/does/not/exist': No such file or directory
201
21hush: can't open '/does/not/exist': No such file or directory
221
23hush: can't open '/does/not/exist': No such file or directory
241
25hush: can't open '/does/not/exist': No such file or directory
261
27Done: a=b
diff --git a/shell/hush_test/hush-psubst/falsetick.tests b/shell/hush_test/hush-psubst/falsetick.tests
new file mode 100755
index 000000000..44d2eae8b
--- /dev/null
+++ b/shell/hush_test/hush-psubst/falsetick.tests
@@ -0,0 +1,22 @@
1# Exitcode 0 (`` has no exitcode, but assignment has):
2true; a=``; echo $?
3false; a=``; echo $?
4true; a=$(); echo $?
5false; a=$(); echo $?
6# Exitcode 2 (`cmd` expansion sets exitcode after assignment set it to 0):
7true; a=`exit 2`; echo $?
8false; a=`exit 2`; echo $?
9true; a=$(exit 2); echo $?
10false; a=$(exit 2); echo $?
11# Exitcode 1 (redirect sets exitcode to 1 on error after them):
12true; a=`` >/does/not/exist; echo $?
13false; a=`` >/does/not/exist; echo $?
14true; a=$() >/does/not/exist; echo $?
15false; a=$() >/does/not/exist; echo $?
16true; a=`exit 2` >/does/not/exist; echo $?
17false; a=`exit 2` >/does/not/exist; echo $?
18true; a=$(exit 2) >/does/not/exist; echo $?
19false; a=$(exit 2) >/does/not/exist; echo $?
20# ...and assignment still happens despite redirect error:
21true; a=$(echo b) >/does/not/exist; echo $?
22echo "Done: a=$a"