Welcome to mirror list, hosted at ThFree Co, Russian Federation.

cygwin.com/git/newlib-cygwin.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTakashi Yano <takashi.yano@nifty.ne.jp>2022-02-15 17:23:50 +0300
committerTakashi Yano <takashi.yano@nifty.ne.jp>2022-02-20 13:21:51 +0300
commit2cab4d0bb4af5ad7ec97914068d5fa1b8954909c (patch)
treee6c43b64c1c7c6d979ec87c4c737bf01cd0b9190 /winsup/cygwin/fhandler_console.cc
parent416792d59a660d45cbfe822392bc9be0bf9da966 (diff)
Cygwin: pty, console: Refactor the code processing special keys.
- This patch commonize the code which processes special keys in pty and console to improve maintanancibility. As a result, some small bugs have been fixed.
Diffstat (limited to 'winsup/cygwin/fhandler_console.cc')
-rw-r--r--winsup/cygwin/fhandler_console.cc135
1 files changed, 49 insertions, 86 deletions
diff --git a/winsup/cygwin/fhandler_console.cc b/winsup/cygwin/fhandler_console.cc
index 50f350c49..475c1acdb 100644
--- a/winsup/cygwin/fhandler_console.cc
+++ b/winsup/cygwin/fhandler_console.cc
@@ -188,13 +188,28 @@ cons_master_thread (VOID *arg)
void
fhandler_console::cons_master_thread (handle_set_t *p, tty *ttyp)
{
+ termios &ti = ttyp->ti;
DWORD output_stopped_at = 0;
while (con.owner == myself->pid)
{
DWORD total_read, n, i;
INPUT_RECORD input_rec[INREC_SIZE];
- if (con.disable_master_thread)
+ bool nat_fg = false;
+ bool nat_child_fg = false;
+ winpids pids ((DWORD) 0);
+ for (unsigned i = 0; i < pids.npids; i++)
+ {
+ _pinfo *pi = pids[i];
+ if (pi && pi->ctty == ttyp->ntty && pi->pgid == ttyp->getpgid ()
+ && (pi->process_state & PID_NOTCYGWIN)
+ && !(pi->process_state & PID_NEW_PG))
+ nat_fg = true;
+ if (pi && pi->ctty == ttyp->ntty && pi->pgid == ttyp->getpgid ()
+ && !(pi->process_state & PID_CYGPARENT))
+ nat_child_fg = true;
+ }
+ if (nat_fg && !nat_child_fg)
{
cygwait (40);
continue;
@@ -233,90 +248,35 @@ fhandler_console::cons_master_thread (handle_set_t *p, tty *ttyp)
}
for (i = 0; i < total_read; i++)
{
- const wchar_t wc = input_rec[i].Event.KeyEvent.uChar.UnicodeChar;
- if ((wint_t) wc >= 0x80)
- continue;
- char c = (char) wc;
+ wchar_t wc;
+ char c;
+ bool was_output_stopped;
bool processed = false;
- termios &ti = ttyp->ti;
- pinfo pi (ttyp->getpgid ());
- if (pi && pi->ctty == ttyp->ntty
- && (pi->process_state & PID_NOTCYGWIN)
- && input_rec[i].EventType == KEY_EVENT && c == '\003')
- {
- bool not_a_sig = false;
- if (!CCEQ (ti.c_cc[VINTR], c)
- && !CCEQ (ti.c_cc[VQUIT], c)
- && !CCEQ (ti.c_cc[VSUSP], c))
- not_a_sig = true;
- if (input_rec[i].Event.KeyEvent.bKeyDown)
- {
- /* CTRL_C_EVENT does not work for the process started with
- CREATE_NEW_PROCESS_GROUP flag, so send CTRL_BREAK_EVENT
- instead. */
- if (pi->process_state & PID_NEW_PG)
- GenerateConsoleCtrlEvent (CTRL_BREAK_EVENT,
- pi->dwProcessId);
- else
- GenerateConsoleCtrlEvent (CTRL_C_EVENT, 0);
- if (not_a_sig)
- goto skip_writeback;
- }
- processed = true;
- if (not_a_sig)
- goto remove_record;
- }
switch (input_rec[i].EventType)
{
case KEY_EVENT:
- if (ti.c_lflag & ISIG)
- {
- int sig = 0;
- if (CCEQ (ti.c_cc[VINTR], c))
- sig = SIGINT;
- else if (CCEQ (ti.c_cc[VQUIT], c))
- sig = SIGQUIT;
- else if (CCEQ (ti.c_cc[VSUSP], c))
- sig = SIGTSTP;
- if (sig && input_rec[i].Event.KeyEvent.bKeyDown)
- {
- ttyp->kill_pgrp (sig);
- ttyp->output_stopped = false;
- ti.c_lflag &= ~FLUSHO;
- /* Discard type ahead input */
- goto skip_writeback;
- }
- }
- if (ti.c_iflag & IXON)
- {
- if (CCEQ (ti.c_cc[VSTOP], c))
- {
- if (!ttyp->output_stopped
- && input_rec[i].Event.KeyEvent.bKeyDown)
- {
- ttyp->output_stopped = true;
- output_stopped_at = i;
- }
- processed = true;
- }
- else if (CCEQ (ti.c_cc[VSTART], c))
- {
- restart_output:
- if (input_rec[i].Event.KeyEvent.bKeyDown)
- ttyp->output_stopped = false;
- processed = true;
- }
- else if ((ti.c_iflag & IXANY) && ttyp->output_stopped
- && c && i >= output_stopped_at)
- goto restart_output;
- }
- if ((ti.c_lflag & ICANON) && (ti.c_lflag & IEXTEN)
- && CCEQ (ti.c_cc[VDISCARD], c))
+ if (!input_rec[i].Event.KeyEvent.bKeyDown)
+ continue;
+ wc = input_rec[i].Event.KeyEvent.uChar.UnicodeChar;
+ if (!wc || (wint_t) wc >= 0x80)
+ continue;
+ c = (char) wc;
+ switch (process_sigs (c, ttyp, NULL))
{
- if (input_rec[i].Event.KeyEvent.bKeyDown)
- ti.c_lflag ^= FLUSHO;
+ case signalled:
+ case not_signalled_but_done:
processed = true;
+ ttyp->output_stopped = false;
+ if (ti.c_lflag & NOFLSH)
+ goto remove_record;
+ goto skip_writeback;
+ default: /* not signalled */
+ break;
}
+ was_output_stopped = ttyp->output_stopped;
+ processed = process_stop_start (c, ttyp, i > output_stopped_at);
+ if (!was_output_stopped && ttyp->output_stopped)
+ output_stopped_at = i;
break;
case WINDOW_BUFFER_SIZE_EVENT:
SHORT y = con.dwWinSize.Y;
@@ -447,7 +407,6 @@ fhandler_console::setup ()
con.cons_rapoi = NULL;
shared_console_info->tty_min_state.is_console = true;
con.cursor_key_app_mode = false;
- con.disable_master_thread = false;
}
}
@@ -503,8 +462,6 @@ fhandler_console::set_input_mode (tty::cons_mode m, const termios *t,
flags |= ENABLE_VIRTUAL_TERMINAL_INPUT;
else
flags |= ENABLE_MOUSE_INPUT;
- if (shared_console_info)
- con.disable_master_thread = false;
break;
case tty::native:
if (t->c_lflag & ECHO)
@@ -517,8 +474,6 @@ fhandler_console::set_input_mode (tty::cons_mode m, const termios *t,
flags &= ~ENABLE_ECHO_INPUT;
if (t->c_lflag & ISIG)
flags |= ENABLE_PROCESSED_INPUT;
- if (shared_console_info)
- con.disable_master_thread = true;
break;
}
SetConsoleMode (p->input_handle, flags);
@@ -1394,9 +1349,6 @@ fhandler_console::open (int flags, mode_t)
setenv ("TERM", "cygwin", 1);
}
- set_input_mode (tty::cygwin, &get_ttyp ()->ti, &handle_set);
- set_output_mode (tty::cygwin, &get_ttyp ()->ti, &handle_set);
-
debug_printf ("opened conin$ %p, conout$ %p", get_handle (),
get_output_handle ());
@@ -1421,6 +1373,17 @@ fhandler_console::open_setup (int flags)
return fhandler_base::open_setup (flags);
}
+void
+fhandler_console::post_open_setup (int fd)
+{
+ if (fd == 0)
+ set_input_mode (tty::cygwin, &get_ttyp ()->ti, &handle_set);
+ else if (fd == 1 || fd == 2)
+ set_output_mode (tty::cygwin, &get_ttyp ()->ti, &handle_set);
+
+ fhandler_base::post_open_setup (fd);
+}
+
int
fhandler_console::close ()
{