From 63bb934c9e48d3ba1dc7f8001d423ea84b9a00c2 Mon Sep 17 00:00:00 2001 From: Marian Buschsieweke Date: Thu, 19 Jan 2023 17:18:18 +0100 Subject: [PATCH] lineedit: Handle SIGWINCH gracefully Since 1.16.0 a resize of the terminal emulator resulted in ash printing a new command line. This fixes the issue by retrying read_key() in lineedit_read_key() on SIGWINCH, rendering reception of SIGWINCH transparent to callers of read_line_input(). Fixes https://bugs.busybox.net/show_bug.cgi?id=15256 --- libbb/lineedit.c | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/libbb/lineedit.c b/libbb/lineedit.c index d6b2e76ff..a47d9e508 100644 --- a/libbb/lineedit.c +++ b/libbb/lineedit.c @@ -2149,7 +2149,7 @@ static void cmdedit_setwidth(void) redraw((new_y >= cmdedit_y ? new_y : cmdedit_y), command_len - cursor); } -static void win_changed(int nsig UNUSED_PARAM) +static void win_changed(int nsig) { if (S.ok_to_redraw) { /* We are in read_key(), safe to redraw immediately */ @@ -2157,6 +2157,7 @@ static void win_changed(int nsig UNUSED_PARAM) cmdedit_setwidth(); fflush_all(); errno = sv_errno; + bb_got_signal = nsig; } else { /* Signal main loop that redraw is necessary */ S.SIGWINCH_count++; @@ -2186,7 +2187,9 @@ static int lineedit_read_key(char *read_key_buffer, int timeout) * Note: read_key sets errno to 0 on success. */ for (;;) { - if ((state->flags & LI_INTERRUPTIBLE) && bb_got_signal) { + if ((state->flags & LI_INTERRUPTIBLE) && bb_got_signal + && (bb_got_signal != SIGWINCH) + ) { errno = EINTR; return -1; } @@ -2197,6 +2200,10 @@ static int lineedit_read_key(char *read_key_buffer, int timeout) IF_FEATURE_EDITING_WINCH(S.ok_to_redraw = 0;) if (errno != EINTR) break; + if (bb_got_signal == SIGWINCH) { + bb_got_signal = 0; + continue; + } if (state->flags & LI_INTERRUPTIBLE) { /* LI_INTERRUPTIBLE bails out on EINTR, * but nothing really guarantees that bb_got_signal -- 2.39.1