aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--shell/ash.c1
-rw-r--r--shell/hush.c26
2 files changed, 22 insertions, 5 deletions
diff --git a/shell/ash.c b/shell/ash.c
index 15246f55f..3e5a3b3e9 100644
--- a/shell/ash.c
+++ b/shell/ash.c
@@ -9876,6 +9876,7 @@ preadfd(void)
raise(SIGINT);
return 1;
}
+ exitstatus = 128 + SIGINT;
goto retry;
}
if (nr < 0) {
diff --git a/shell/hush.c b/shell/hush.c
index 2f07f4ac1..5b720ce98 100644
--- a/shell/hush.c
+++ b/shell/hush.c
@@ -1746,6 +1746,7 @@ static int check_and_run_traps(void)
argv[2] = NULL;
save_rcode = G.last_exitcode;
builtin_eval(argv);
+//FIXME: shouldn't it be set to 128 + sig instead?
G.last_exitcode = save_rcode;
last_sig = sig;
} /* else: "" trap, ignoring signal */
@@ -2192,7 +2193,7 @@ static int get_user_input(struct in_str *i)
prompt_str = setup_prompt_string(i->promptmode);
# if ENABLE_FEATURE_EDITING
- do {
+ for (;;) {
reinit_unicode_for_hush();
G.flag_SIGINT = 0;
/* buglet: SIGINT will not make new prompt to appear _at once_,
@@ -2201,9 +2202,15 @@ static int get_user_input(struct in_str *i)
G.user_input_buf, CONFIG_FEATURE_EDITING_MAX_LEN-1,
/*timeout*/ -1
);
- /* catch *SIGINT* etc (^C is handled by read_line_input) */
+ /* read_line_input intercepts ^C, "convert" it into SIGINT */
+ if (r == 0)
+ raise(SIGINT);
check_and_run_traps();
- } while (r == 0 || G.flag_SIGINT); /* repeat if ^C or SIGINT */
+ if (r != 0 && !G.flag_SIGINT)
+ break;
+ /* ^C or SIGINT: repeat */
+ G.last_exitcode = 128 + SIGINT;
+ }
if (r < 0) {
/* EOF/error detected */
i->p = NULL;
@@ -2213,7 +2220,7 @@ static int get_user_input(struct in_str *i)
i->p = G.user_input_buf;
return (unsigned char)*i->p++;
# else
- do {
+ for (;;) {
G.flag_SIGINT = 0;
if (i->last_char == '\0' || i->last_char == '\n') {
/* Why check_and_run_traps here? Try this interactively:
@@ -2226,7 +2233,16 @@ static int get_user_input(struct in_str *i)
}
fflush_all();
r = fgetc(i->file);
- } while (G.flag_SIGINT || r == '\0');
+ /* In !ENABLE_FEATURE_EDITING we don't use read_line_input,
+ * no ^C masking happens during fgetc, no special code for ^C:
+ * it generates SIGINT as usual.
+ */
+ check_and_run_traps();
+ if (G.flag_SIGINT)
+ G.last_exitcode = 128 + SIGINT;
+ if (r != '\0')
+ break;
+ }
return r;
# endif
}