getty: explain every bit in termios; remove redundant stuff in termios_final
authorDenys Vlasenko <vda.linux@googlemail.com>
Wed, 26 Jan 2011 02:26:38 +0000 (03:26 +0100)
committerDenys Vlasenko <vda.linux@googlemail.com>
Wed, 26 Jan 2011 02:26:38 +0000 (03:26 +0100)
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
console-tools/resize.c
loginutils/getty.c

index fdfe2a6..ee0728b 100644 (file)
@@ -53,6 +53,7 @@ int resize_main(int argc UNUSED_PARAM, char **argv UNUSED_PARAM)
         */
        fprintf(stderr, ESC"7" ESC"[r" ESC"[999;999H" ESC"[6n");
        alarm(3); /* Just in case terminal won't answer */
+//BUG: death by signal won't restore termios
        scanf(ESC"[%hu;%huR", &w.ws_row, &w.ws_col);
        fprintf(stderr, ESC"8");
 
index b71d68a..29d889f 100644 (file)
@@ -106,15 +106,15 @@ struct globals {
 //usage:#define getty_full_usage "\n\n"
 //usage:       "Open a tty, prompt for a login name, then invoke /bin/login\n"
 //usage:     "\nOptions:"
-//usage:     "\n       -h              Enable hardware (RTS/CTS) flow control"
-//usage:     "\n       -i              Don't display /etc/issue"
-//usage:     "\n       -L              Local line, set CLOCAL on it"
+//usage:     "\n       -h              Enable hardware RTS/CTS flow control"
+//usage:     "\n       -L              Set CLOCAL (ignore Carrier Detect state)"
 //usage:     "\n       -m              Get baud rate from modem's CONNECT status message"
+//usage:     "\n       -n              Don't prompt for login name"
 //usage:     "\n       -w              Wait for CR or LF before sending /etc/issue"
-//usage:     "\n       -n              Don't prompt for a login name"
+//usage:     "\n       -i              Don't display /etc/issue"
 //usage:     "\n       -f ISSUE_FILE   Display ISSUE_FILE instead of /etc/issue"
 //usage:     "\n       -l LOGIN        Invoke LOGIN instead of /bin/login"
-//usage:     "\n       -t SEC          Terminate after SEC if no username is read"
+//usage:     "\n       -t SEC          Terminate after SEC if no login name is read"
 //usage:     "\n       -I INITSTR      Send INITSTR before anything else"
 //usage:     "\n       -H HOST         Log HOST into the utmp file as the hostname"
 //usage:     "\n"
@@ -251,21 +251,28 @@ static void termios_init(int speed)
         * reads will be done in raw mode anyway. Errors will be dealt with
         * later on.
         */
+       /* 8 bits; hangup (drop DTR) on last close; enable receive */
        G.termios.c_cflag = CS8 | HUPCL | CREAD;
-       if (option_mask32 & F_LOCAL)
+       if (option_mask32 & F_LOCAL) {
+               /* ignore Carrier Detect pin:
+                * opens don't block when CD is low,
+                * losing CD doesn't hang up processes whose ctty is this tty
+                */
                G.termios.c_cflag |= CLOCAL;
+       }
+#ifdef CRTSCTS
+       if (option_mask32 & F_RTSCTS)
+               G.termios.c_cflag |= CRTSCTS; /* flow control using RTS/CTS pins */
+#endif
        G.termios.c_iflag = 0;
        G.termios.c_lflag = 0;
+       /* non-raw output; add CR to each NL */
        G.termios.c_oflag = OPOST | ONLCR;
-       G.termios.c_cc[VMIN] = 1;
-       G.termios.c_cc[VTIME] = 0;
+       G.termios.c_cc[VMIN] = 1; /* block reads if < 1 char is available */
+       G.termios.c_cc[VTIME] = 0; /* no timeout (reads block forever) */
 #ifdef __linux__
        G.termios.c_line = 0;
 #endif
-#ifdef CRTSCTS
-       if (option_mask32 & F_RTSCTS)
-               G.termios.c_cflag |= CRTSCTS;
-#endif
 
        tcsetattr_stdin_TCSANOW(&G.termios);
 
@@ -274,12 +281,17 @@ static void termios_init(int speed)
 
 static void termios_final(void)
 {
-       /* General terminal-independent stuff */
-       G.termios.c_iflag |= IXON | IXOFF;    /* 2-way flow control */
+       /* software flow control on output; and on input */
+       G.termios.c_iflag |= IXON | IXOFF;
+       if (G.eol == '\r') {
+               G.termios.c_iflag |= ICRNL; /* map CR on input to NL */
+       }
+       /* non-raw input; enable SIGINT/QUIT/ec sigs; echo; echo NL on kill char;
+        * erase entire line via BS-space-BS on kill char */
        G.termios.c_lflag |= ICANON | ISIG | ECHO | ECHOE | ECHOK | ECHOKE;
-       /* no longer in lflag: | ECHOCTL | ECHOPRT */
-       G.termios.c_oflag |= OPOST;
-       /* G.termios.c_cflag = 0; */
+       /* echo ctrl chars as ^c; (what is ECHOPRT?) */
+       /* no longer in c_lflag: | ECHOCTL | ECHOPRT */
+
        G.termios.c_cc[VINTR] = DEF_INTR;
        G.termios.c_cc[VQUIT] = DEF_QUIT;
        G.termios.c_cc[VEOF] = DEF_EOF;
@@ -290,22 +302,8 @@ static void termios_final(void)
 #ifdef VSWTCH
        G.termios.c_cc[VSWTCH] = DEF_SWITCH;
 #endif
-
-       /* Account for special characters seen in input */
-       if (G.eol == '\r') {
-               G.termios.c_iflag |= ICRNL;   /* map CR in input to NL */
-               /* already done by termios_init */
-               /* G.termios.c_oflag |= ONLCR; map NL in output to CR-NL */
-       }
        G.termios.c_cc[VKILL] = DEF_KILL;
 
-#ifdef CRTSCTS
-       /* Optionally enable hardware flow control */
-       if (option_mask32 & F_RTSCTS)
-               G.termios.c_cflag |= CRTSCTS;
-#endif
-
-       /* Finally, make the new settings effective */
        if (tcsetattr_stdin_TCSANOW(&G.termios) < 0)
                bb_perror_msg_and_die("tcsetattr");
 }
@@ -330,11 +328,7 @@ static void auto_baud(void)
         * modem status messages is enabled.
         */
 
-       /*
-        * Don't block if input queue is empty.
-        * Errors will be dealt with later on.
-        */
-       G.termios.c_cc[VMIN] = 0;       /* don't block if queue empty */
+       G.termios.c_cc[VMIN] = 0; /* don't block reads (min read is 0 chars) */
        tcsetattr_stdin_TCSANOW(&G.termios);
 
        /*
@@ -538,6 +532,7 @@ int getty_main(int argc UNUSED_PARAM, char **argv)
 
        /* Set the optional timer */
        alarm(G.timeout); /* if 0, alarm is not set */
+//BUG: death by signal won't restore termios
 
        /* Optionally wait for CR or LF before writing /etc/issue */
        if (option_mask32 & F_WAITCRLF) {