270 likes | 717 Views
Terminal I/O. POSIX termios Two terminal I/O modes Canonical and non-canonical Getting and setting terminal attributes Terminal window size: struct winsize. tty. One of the first terminals was the TeleTypeWriter from which we get the abbreviation tty
E N D
Terminal I/O • POSIX termios • Two terminal I/O modes • Canonical and non-canonical • Getting and setting terminal attributes • Terminal window size: struct winsize
tty • One of the first terminals was the TeleTypeWriter from which we get the abbreviation tty • A terminal is usually interactive and can be either local or connected via a network • A tty is connected at two “ends” • For real terminals, one end is connected to hardware, such as the monitor, and the other end to software, such as the shell • Pseudo terminals (covered next time) have both ends connected to software such as telnet etc
Terminal I/O Modes • Canonical mode (aka cooked mode) • Default terminal mode • Provides a simple line editor. Input is sent to application one line at a time • Most UNIX systems implement this in a module known as the “terminal line discipline” • Non-canonical mode (aka raw mode) • Input not assembled into lines. Data passed to application as it is received
Terminal Operations int isatty(int desc); • desc is an open file descriptor • Returns 1 if the FD is connected to a tty device or 0 otherwise char *ttyname(int fd); • Returns the pathname of the terminal device or NULL on error (such as fd is not associated with a tty device)
Terminal Operations char *ctermid(char *s); • Returns the pathname of the controlling terminal. • If s is NULL, static buffer is used • Pass in a buffer of length L_ctermid to avoid the static buffer
termios overview • Structure defined in <termios.h> that contains the terminal device characteristics that we can change struct termios { tcflag_t c_iflag; /* input flags */ tcflag_t c_oflag; /* output flags */ tcflag_t c_cflag; /* control flags */ tcflag_t c_lflag; /* local flags */ cc_t c_cc[NCCS]; /* control chars */ };
termios overview • c_iflag • Input flags. Controls the input of characters by the terminal device driver (strip 8th bit on input, enable parity, etc) • c_oflag • Output flags. Controls driver output (perform output processing, map newline to CR/LF, etc)
termios overview • c_cflag • Control flags. Affect the RS-232 serial lines (ignore modem status lines, one or two stop bits per character, etc) • c_lflag • Local flags. Affect interface between driver and user (echo on or off, visually erase characters, enable terminal-generated signals, job control stop signal for background output, etc)
termios overview • c_cc • An array of special characters we can change such as Ctrl D etc. NCCS is usually 15-20 elements. POSIX defines 11, the rest are implementation specific • cc_t is large enough to hold a special character. Usually an unsigned char • See figs 18.3-18.6 staring on page 635 for list of flags • Fig 18.7 on page 637 lists functions that manipulate these flags
termios overview • tcgetattr - fetch attributes • tcsetattr - set attributes • tcdrain - wait for all output to be transmitted • tcflush - flush pending input and/or output
Special Input Characters • Fig 18.9 on page 638 lists the special input characters • 11 are POSIX standard. Of those, we can not change the value of CR (\r) or NL (\n). The other 9 can be changed
Getting and Setting Terminal Attributes int tcgetattr(int fd, struct termios *termios_p); int tcsetattr(int fd, int optional_actions, const struct termios *termios_p); • termios_p points to a termios structure • optional_actions specifies when to apply the new attributes • TCSANOW - set attributes now • TCSADRAIN – wait for all output to transmit • TCSAFLUSH – flush pending input/output
Terminal Option Flags • Section 18.5 lists the various flags that can be used with the termios structure. See page 645-651 for full list • c_cflg • CSIZE a mask that specifies the number of bits per byte (not including parity bit if used) Values are CS5, CS6, CS7 and CS8 See example on page 644 for usage
Terminal Option Flags • PARENB if set, generates and checks parity for outgoing and incoming characters • PARODD If set, parity is odd, otherwise parity is even • c_lflag • ECHO if set, input characters are echoed back to the terminal device. Can be used in either canonical or non-canonical modes
Terminal Option Flags • ICANON if set, canonical mode is in effect • ECHONL if set, and if ICANON is set, the NL character is echoed, even if ECHO is not set • c_iflag • ISTRIP when set, valid input bytes are stripped to 7 bits. Otherwise all 8 bits are processed • ETC…
stty command • Shell command to examine and modify terminal attributes • stty –a displays all the terminal attributes
Baud Rate Functions • Baud Rate – bits per second • B2400, B9600, B19200, B38400, etc • Get I/O Baud Rate speed_t cfgetispeed(const struct termios *termios_p); speed_t cfgetospeed(const struct termios *termios_p); • Set I/O Baud Rate int cfsetispeed(struct termios *termios_p, speed_t speed); int cfsetospeed(struct termios *termios_p, speed_t speed); • Returns 0 if ok, -1 on error
Line Control Functions • See page 653 for full explanation • int tcdrain(int fd); • int tcflow(int fd, int action); • int tcflush(int fd, int queue_selector); • int tcsendbreak(int fd, int duration);
Canonical Mode • Provides limited line editing. Data sent to application one line at a time • When we issue a read it returns when • The requested number of bytes have been read • A line delimiter is encountered (NL, EOF, EOL, EOL2 and sometimes CR) • A signal is caught but read not automatically restarted
Non-Canonical Mode • Specified by turning off the ICANON flag in the c_lflag field of the termios structure • Input data not assembled into lines • Some characters not processed (ERASE, KILL, EOF, NL, EOL, EOL2, CR, REPRINT, STATUS and WERASE)
Non-Canonical Mode • Two variables (MIN and TIME) in the c_cc array indexed by VMIN and VTIME • MIN - specifies the minimum number of bytes to read before a read returns • TIME – specifies the number of tenths of a second to wait for data to arrive
Terminal Window Size • Most UNIX systems provide a way to keep track of the current terminal window size and have the kernel notify the foreground process group when the size changes struct winsize{ unsigned short ws_row; /* rows in characters */ unsigned short ws_col; /* cols in characters */ unsigned short ws_xpixel /* unused */ unsigned short ws_ypixel /* unused */ };
Terminal Window Size • Current window size can be fetched by calling ioctl with TIOCGWINSZ • Can set a new value by calling ioctl with TIOCSWINSZ. If new value is different than old value it is stored in the kernel and a SIGWINCH is sent to the foreground process group (by default the signal is ignored)