diff --git a/NEWS b/NEWS index f1b8b124b..376413456 100644 --- a/NEWS +++ b/NEWS @@ -9,6 +9,11 @@ Any uppercase BUG_* names are modernish shell bug IDs. script is entirely parsed before (or without) being executed, such as dotted/sourced scripts and scripts compiled by shcomp. +- Added support for the size mode to the stty(1) built-in. This mode is used + to display the terminal's number of rows and columns. Note that the stty + built-in is not compiled in by default. This can be changed by adding + stty to the table of built-ins in src/cmd/ksh93/data/builtins.c. + 2021-11-20: - Listing types with 'typeset -T' no longer displays incomplete versions of diff --git a/src/lib/libcmd/stty.c b/src/lib/libcmd/stty.c index c41c89fb7..9d3563891 100644 --- a/src/lib/libcmd/stty.c +++ b/src/lib/libcmd/stty.c @@ -27,7 +27,7 @@ */ static const char usage[] = -"[-?@(#)$Id: stty (AT&T Research) 2010-04-01 $\n]" +"[-?@(#)$Id: stty (ksh 93u+m) 2021-11-23 $\n]" "[--catalog?" ERROR_CATALOG "]" "[+NAME?stty - set or get terminal modes]" "[+DESCRIPTION?\bstty\b sets certain terminal I/O modes for the device " @@ -110,6 +110,7 @@ static const char usage[] = #define CASE 10 #define TABS 11 #define WIND 12 +#define WINDSZ 13 #undef SS /* who co-opted this namespace? */ @@ -157,6 +158,7 @@ static const Tty_t Ttable[] = { "rows", WIND, W_SIZE, IG, 0, 24, C("\an\a is the number of lines for display") }, { "cols", WIND, W_SIZE, IG, 1, 80, C("\an\a is the number of columns for display") }, { "columns", WIND, W_SIZE, IG, 1, 80, C("Same as \bcols\b") }, +{ "size", WINDSZ, W_SIZE, IG, 2, 0, C("Current terminal window size") }, #endif { "intr", CHAR, T_CHAR, SS, VINTR, 'C', C("Send an interrupt signal") }, { "quit", CHAR, T_CHAR, SS, VQUIT, '|', C("Send a quit signal") }, @@ -703,6 +705,7 @@ static void set(char *argv[], struct termios *sp) break; #ifdef TIOCSWINSZ case WIND: + case WINDSZ: { struct winsize win; int n; @@ -711,11 +714,28 @@ static void set(char *argv[], struct termios *sp) error(ERROR_system(1),"cannot set %s",tp->name); UNREACHABLE(); } - if(!(cp= *argv)) + if(!(cp = *argv)) { - sfprintf(sfstdout,"%d\n",tp->mask?win.ws_col:win.ws_row); + switch(tp->mask) + { + case 0: /* stty rows */ + sfprintf(sfstdout,"%d\n",win.ws_row); + break; + case 1: /* stty cols/stty columns */ + sfprintf(sfstdout,"%d\n",win.ws_col); + break; + case 2: /* stty size */ + sfprintf(sfstdout,"%d %d\n",win.ws_row,win.ws_col); + break; + } break; } + if(tp->mask==2) + { + /* 'stty size' doesn't set the terminal window size */ + error(ERROR_system(1),"%s: invalid argument",argv[0]); + UNREACHABLE(); + } argv++; n=strtol(cp,&cp,10); if(*cp) @@ -898,6 +918,7 @@ static int infof(Opt_t* op, Sfio_t* sp, const char* s, Optdisc_t* dp) sfprintf(sp,"}[+Control Assignments.?If \ac\a is \bundef\b or an empty " "string then the control assignment is disabled.]{"); listchars(sp,WIND); + listmode(sp,"size"); listchars(sp,CHAR); sfprintf(sp,"}[+Combination Modes.]{"); listmode(sp,"ek");