groff
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH] [grotty]: Use terminfo.


From: Lennart Jablonka
Subject: [PATCH] [grotty]: Use terminfo.
Date: Sat, 19 Aug 2023 20:08:06 +0000

This has nothing at all to do with making it easier to customize the
look of man pages.

Use of hardcoded SGR escape sequences persists as a fallback but should
probably be dropped.  If it stays, I’m unsure of the interface to
grotty.  The -T disabling the fallback seems hackish.

Hyperlinks are still marked up using OSC 8, hoping that whatever
terminal sits in front of the user interprets or ignores those.
Terminfo naturally doesn’t have a capability for hyperlinks.

Autoconf is not informed about the depence on Curses; we simply link
with -lcurses, as that is what X/Open Curses specifies.

The suggested option to less is changed to -r, which enables passing
through single control characters, because some terminal descriptions
use those; I noticed that xterm’s sgr0 contains ^O.

I’m too lazy to find another name for lines_.
---
Hey Branden!

All this NEWS and ChangeLog and Autotools GNU stuff is confusing.
Do as you wish with it.

I didn’t test this a whole lot, much less wrote automated tests.
Have fun.

PS: There doesn’t happen to be a convention on whether to use 
non-ASCII characters in commit messages, right?  Seeing as you, 
Branden, yourself aren’t always quite consistent with that.

PPS: Mandoc underlines italic \~s.

        .RI [ file\~ .\|.\|.]

is rendered as

        [_f_i_l_e_ ...]

by mandoc.  Just noticed that.

 INSTALL.extra                   |   5 +-
 NEWS                            |   9 +
 src/devices/grotty/grotty.1.man |  43 ++++-
 src/devices/grotty/grotty.am    |   3 +-
 src/devices/grotty/tty.cpp      | 293 +++++++++++++++-----------------
 5 files changed, 188 insertions(+), 165 deletions(-)

diff --git a/INSTALL.extra b/INSTALL.extra
index 78d4139af..3527b1929 100644
--- a/INSTALL.extra
+++ b/INSTALL.extra
@@ -122,12 +122,15 @@ Several programs distributed with GNU roff are written in 
the Perl
 language.  Version 5.6.1 (1 April 2001) or later is required.
 
 The 'uchardet' library is an optional dependency of the 'preconv'
-program: if this library is found by 'configure', it will be
+program: If this library is found by 'configure', it will be
 automatically used by 'preconv'.  Discovery of the 'uchardet' library
 requires the 'pkg-config' program to be installed on your system, as
 well as the library's C header files--on a package-based host system,
 this can mean installing uchardet's '-dev' or '-devel' package.
 
+The 'grotty' program depends on a Curses library, which is specified
+by X/Open Curses.
+
 URW fonts
 ---------
 
diff --git a/NEWS b/NEWS
index ae0fedb8c..dcc75f233 100644
--- a/NEWS
+++ b/NEWS
@@ -80,6 +80,15 @@ o The s (ms) macro package now sets the vertical spacing 
register
   document with a type size of 20 points, the vertical spacing now
   defaults to 24 points rather than 22.
 
+Output drivers
+--------------
+
+grotty
+------
+
+o The terminfo library is now used for applying text attributes (like
+  italic, bold, and colors).
+
 Miscellaneous
 -------------
 
diff --git a/src/devices/grotty/grotty.1.man b/src/devices/grotty/grotty.1.man
index 41eabbcfa..ebdfd1639 100644
--- a/src/devices/grotty/grotty.1.man
+++ b/src/devices/grotty/grotty.1.man
@@ -56,6 +56,8 @@ output driver for typewriter-like (terminal) devices
 .RB [ \-i \||\| \-r ]
 .RB [ \-F\~\c
 .IR font-directory ]
+.RB [ \-T\~\c
+.IR term ]
 .RI [ file\~ .\|.\|.]
 .YS
 .
@@ -64,6 +66,8 @@ output driver for typewriter-like (terminal) devices
 .RB [ \-bBdfhouU ]
 .RB [ \-F\~\c
 .IR font-directory ]
+.RB [ \-T\~\c
+.IR term ]
 .RI [ file\~ .\|.\|.]
 .YS
 .
@@ -136,9 +140,8 @@ Output is written to the standard output stream.
 .P
 By default,
 .I grotty
-emits SGR escape sequences
-(from ISO\~6429,
-popularly called \[lq]ANSI escapes\[rq])
+uses
+.MR terminfo 5
 to change text attributes
 (bold,
 italic,
@@ -148,6 +151,15 @@ reverse video
 [\[lq]negative image\[rq]]
 and colors).
 .
+If no
+.I TERM
+environment variable is set
+or terminfo encounters a different error,
+.I grotty
+emits hardcoded SGR escape sequences
+(from ISO\~6429,
+popularly called \[lq]ANSI escapes\[rq]).
+.
 Devices supporting the appropriate sequences can view
 .I roff
 documents using eight different background and foreground colors.
@@ -188,10 +200,10 @@ When paging
 .IR grotty 's
 output with
 .MR less 1 ,
-the latter program must be instructed to pass SGR and OSC sequences
+the latter program must be instructed to pass control characters
 through to the device;
 its
-.B \-R
+.B \-r
 option is one way to achieve this
 .RI ( less
 version 566 or later is required for OSC\~8 support).
@@ -535,6 +547,21 @@ is also specified.
 .
 .
 .TP
+.BI \-T\~ term
+Read description for terminal type
+.I term
+and fail if
+.I terminfo
+encounters and error.
+By default,
+.I grotty
+takes the terminal type from the environment variable
+.I TERM
+and falls back to SGR escape sequences
+if that is not specified or there is an error.
+.
+.
+.TP
 .B \-u
 Suppress the use of underlining for italic characters in legacy output
 format.
@@ -570,6 +597,12 @@ option were specified;
 see subsection \[lq]Legacy output format\[rq] above.
 .
 .
+.TP
+.I TERM
+The terminal type for
+.I terminfo.
+.
+.
 .br
 .ne 3v \" Keep section heading and paragraph tag together.
 .\" ====================================================================
diff --git a/src/devices/grotty/grotty.am b/src/devices/grotty/grotty.am
index 14921c562..a9d2fe1c1 100644
--- a/src/devices/grotty/grotty.am
+++ b/src/devices/grotty/grotty.am
@@ -20,7 +20,8 @@ grotty_SOURCES = src/devices/grotty/tty.cpp
 grotty_LDADD = $(LIBM) \
   libdriver.a \
   libgroff.a \
-  lib/libgnu.a
+  lib/libgnu.a \
+  -lcurses
 man1_MANS += src/devices/grotty/grotty.1
 EXTRA_DIST += \
   src/devices/grotty/grotty.1.man \
diff --git a/src/devices/grotty/tty.cpp b/src/devices/grotty/tty.cpp
index 1b92ad8c0..9df35d8cd 100644
--- a/src/devices/grotty/tty.cpp
+++ b/src/devices/grotty/tty.cpp
@@ -21,6 +21,8 @@ along with this program.  If not, see 
<http://www.gnu.org/licenses/>. */
 #include "device.h"
 #include "ptable.h"
 
+#include <term.h>
+
 typedef signed char schar;
 
 declare_ptable(schar)
@@ -28,8 +30,6 @@ implement_ptable(schar)
 
 extern "C" const char *Version_string;
 
-#define putstring(s) fputs(s, stdout)
-
 #ifndef SHRT_MIN
 #define SHRT_MIN (-32768)
 #endif
@@ -38,7 +38,7 @@ extern "C" const char *Version_string;
 #define SHRT_MAX 32767
 #endif
 
-#define TAB_WIDTH 8
+static int tab_width = 8;
 
 // A character of the output device fits in a 32-bit word.
 typedef unsigned int output_character;
@@ -56,10 +56,16 @@ static bool do_sgr_italics;
 static bool want_reverse_video_for_italics = false;
 static bool do_reverse_video;
 static bool use_overstriking_drawing_scheme = false;
+static bool use_terminfo;
+static char *terminal_name;
 
 static void update_options();
 static void usage(FILE *stream);
 
+// TODO(humm): We can get proper line drawing characters from terminfo
+// using acsc, smacs, rmacs; we could do that for -Tascii + terminfo.
+// There are other characters there we could theoreticlly use as well,
+// like degree and pi.
 static int hline_char = '-';
 static int vline_char = '|';
 
@@ -89,18 +95,16 @@ static unsigned char bold_underline_mode;
 #endif
 
 // SGR handling (ISO 6429)
-#define SGR_BOLD CSI "1m"
-#define SGR_NO_BOLD CSI "22m"
-#define SGR_ITALIC CSI "3m"
-#define SGR_NO_ITALIC CSI "23m"
-#define SGR_UNDERLINE CSI "4m"
-#define SGR_NO_UNDERLINE CSI "24m"
-#define SGR_REVERSE CSI "7m"
-#define SGR_NO_REVERSE CSI "27m"
+// bold and reverse can be unset separately using ISO 6429, but not
+// with terminfo
+static const char *sgr_bold = CSI "1m";
+static const char *sgr_italic = CSI "3m";
+static const char *sgr_underline = CSI "4m";
+static const char *sgr_reverse = CSI "7m";
 // many terminals can't handle 'CSI 39 m' and 'CSI 49 m' to reset
 // the foreground and background color, respectively; we thus use
 // 'CSI 0 m' exclusively
-#define SGR_DEFAULT CSI "0m"
+static const char *sgr_exit_attributes = CSI "0m";
 
 #define DEFAULT_COLOR_IDX -1
 
@@ -172,7 +176,7 @@ public:
 
 
 class tty_printer : public printer {
-  tty_glyph **lines;
+  tty_glyph **lines_; // clashes with Curses lines
   int nlines;
   int cached_v;
   int cached_vpos;
@@ -182,8 +186,7 @@ class tty_printer : public printer {
   bool is_boldfacing;
   bool is_continuously_underlining;
   PTABLE(schar) tty_colors;
-  void make_underline(int);
-  void make_bold(output_character, int);
+  void update_attributes(bool, bool, schar, schar, output_character, int);
   schar color_to_idx(color *);
   void add_char(output_character, int, int, int, color *, color *,
                unsigned char);
@@ -201,10 +204,8 @@ public:
   void set_char(glyph *, font *, const environment *, int, const char *);
   void draw(int, int *, int, const environment *);
   void special(char *, const environment *, char);
-  void change_color(const environment * const);
   void change_fill_color(const environment * const);
   void put_char(output_character);
-  void put_color(schar, int);
   void begin_page(int) { }
   void end_page(int);
   font *make_font(const char *);
@@ -271,54 +272,91 @@ tty_printer::tty_printer() : cached_v(0)
   (void)tty_color(color::MAX_COLOR_VAL, 0, color::MAX_COLOR_VAL, &dummy, 5);
   (void)tty_color(0, color::MAX_COLOR_VAL, color::MAX_COLOR_VAL, &dummy, 6);
   nlines = 66;
-  lines = new tty_glyph *[nlines];
+  lines_ = new tty_glyph *[nlines];
   for (int i = 0; i < nlines; i++)
-    lines[i] = 0;
+    lines_[i] = 0;
   is_continuously_underlining = false;
 }
 
 tty_printer::~tty_printer()
 {
-  delete[] lines;
+  delete[] lines_;
 }
 
-void tty_printer::make_underline(int w)
+/* Update the current text attributes, doing little more than necessary
+work.  The c and w parameters are not used unless
+use_overstriking_drawing_scheme and at least one of underline and bold
+is set. */
+void tty_printer::update_attributes(bool underline, bool bold,
+                                   schar fore_idx, schar back_idx,
+                                   output_character c, int w)
 {
   if (use_overstriking_drawing_scheme) {
-    if (!w)
-      warning("can't underline zero-width character");
-    else {
-      putchar('_');
-      putchar('\b');
+    if (underline) {
+      if (!w)
+       warning("can't underline zero-width character");
+      else {
+       putchar('_');
+       putchar('\b');
+      }
+    }
+    if (bold) {
+      if (!w)
+       warning("can't print zero-width character in bold");
+      else {
+       put_char(c);
+       putchar('\b');
+      }
     }
   }
   else {
-    if (!is_underlining) {
+    if (is_underlining && !underline
+       || is_boldfacing && !bold
+       || curr_fore_idx != DEFAULT_COLOR_IDX && fore_idx == DEFAULT_COLOR_IDX
+       || curr_back_idx != DEFAULT_COLOR_IDX && back_idx == DEFAULT_COLOR_IDX) 
{
+      putp(sgr_exit_attributes);
+      is_underlining = is_boldfacing = false;
+      curr_fore_idx = curr_back_idx = DEFAULT_COLOR_IDX;
+    }
+
+    if (!is_underlining && underline) {
       if (do_sgr_italics)
-       putstring(SGR_ITALIC);
+       putp(sgr_italic);
       else if (do_reverse_video)
-       putstring(SGR_REVERSE);
+       putp(sgr_reverse);
       else
-       putstring(SGR_UNDERLINE);
+       putp(sgr_underline);
+      is_underlining = true;
     }
-    is_underlining = true;
-  }
-}
 
-void tty_printer::make_bold(output_character c, int w)
-{
-  if (use_overstriking_drawing_scheme) {
-    if (!w)
-      warning("can't print zero-width character in bold");
-    else {
-      put_char(c);
-      putchar('\b');
+    if (!is_boldfacing && bold) {
+      putp(sgr_bold);
+      is_boldfacing = true;
+    }
+
+    if (curr_fore_idx != fore_idx) {
+      if (use_terminfo)
+       putp(tparm(set_a_foreground, fore_idx, 0, 0, 0, 0, 0, 0, 0, 0));
+      else {
+       fputs(CSI, stdout);
+       putchar('3');
+       putchar(fore_idx + '0');
+       putchar('m');
+      }
+      curr_fore_idx = fore_idx;
+    }
+
+    if (curr_back_idx != back_idx) {
+      if (use_terminfo)
+       putp(tparm(set_a_background, back_idx, 0, 0, 0, 0, 0, 0, 0, 0));
+      else {
+       fputs(CSI, stdout);
+       putchar('4');
+       putchar(back_idx + '0');
+       putchar('m');
+      }
+      curr_back_idx = back_idx;
     }
-  }
-  else {
-    if (!is_boldfacing)
-      putstring(SGR_BOLD);
-    is_boldfacing = true;
   }
 }
 
@@ -372,11 +410,11 @@ void tty_printer::add_char(output_character c, int w,
            " quantum");
     vpos = v / font::vert;
     if (vpos > nlines) {
-      tty_glyph **old_lines = lines;
-      lines = new tty_glyph *[vpos + 1];
-      memcpy(lines, old_lines, nlines * sizeof(tty_glyph *));
+      tty_glyph **old_lines = lines_;
+      lines_ = new tty_glyph *[vpos + 1];
+      memcpy(lines_, old_lines, nlines * sizeof(tty_glyph *));
       for (int i = nlines; i <= vpos; i++)
-       lines[i] = 0;
+       lines_[i] = 0;
       delete[] old_lines;
       nlines = vpos + 1;
     }
@@ -403,7 +441,7 @@ void tty_printer::add_char(output_character c, int w,
   // at each hpos, and otherwise in order of occurrence.
 
   tty_glyph **pp;
-  for (pp = lines + (vpos - 1); *pp; pp = &(*pp)->next)
+  for (pp = lines_ + (vpos - 1); *pp; pp = &(*pp)->next)
     if ((*pp)->hpos < hpos
        || ((*pp)->hpos == hpos && (*pp)->order() >= g->order()))
       break;
@@ -458,6 +496,8 @@ void tty_printer::special(char *arg, const environment 
*env, char type)
 // repeated arbitrarily and are separated by colons.  Omission of the
 // URI ends the hyperlink that was begun by specifying it.  See
 // <https://gist.github.com/egmontkob/eb114294efbcd5adb1944c9f3cb5feda>.
+//
+// TODO(humm): What should be done with OSC 8 when using terminfo?
 void tty_printer::special_link(const char *arg, const environment *env)
 {
   static bool is_link_active = false;
@@ -522,11 +562,6 @@ void tty_printer::special_link(const char *arg, const 
environment *env)
     simple_add_char(*s, env);
 }
 
-void tty_printer::change_color(const environment * const env)
-{
-  add_char(0, 0, env->hpos, env->vpos, env->col, env->fill, COLOR_CHANGE);
-}
-
 void tty_printer::change_fill_color(const environment * const env)
 {
   add_char(0, 0, env->hpos, env->vpos, env->col, env->fill, COLOR_CHANGE);
@@ -683,42 +718,12 @@ void tty_printer::put_char(output_character wc)
     do *++p = (unsigned char)(((wc >> (6 * --count)) & 0x3f) | 0x80);
       while (count > 0);
     *++p = '\0';
-    putstring(buf);
+    fputs(buf, stdout);
   }
   else
     putchar(wc);
 }
 
-void tty_printer::put_color(schar color_index, int back)
-{
-  if (color_index == DEFAULT_COLOR_IDX) {
-    putstring(SGR_DEFAULT);
-    // set bold and underline again
-    if (is_boldfacing)
-      putstring(SGR_BOLD);
-    if (is_underlining) {
-      if (do_sgr_italics)
-       putstring(SGR_ITALIC);
-      else if (do_reverse_video)
-       putstring(SGR_REVERSE);
-      else
-       putstring(SGR_UNDERLINE);
-    }
-    // set other color again
-    back = !back;
-    color_index = back ? curr_back_idx : curr_fore_idx;
-  }
-  if (color_index != DEFAULT_COLOR_IDX) {
-    putstring(CSI);
-    if (back)
-      putchar('4');
-    else
-      putchar('3');
-    putchar(color_index + '0');
-    putchar('m');
-  }
-}
-
 // The possible Unicode combinations for crossing characters.
 //
 // '  ' = 0, ' -' = 4, '- ' = 8, '--' = 12,
@@ -741,7 +746,7 @@ void tty_printer::end_page(int page_length)
   int lines_per_page = page_length / font::vert;
   int last_line;
   for (last_line = nlines; last_line > 0; last_line--)
-    if (lines[last_line - 1])
+    if (lines_[last_line - 1])
       break;
 #if 0
   if (last_line > lines_per_page) {
@@ -757,8 +762,8 @@ void tty_printer::end_page(int page_length)
   }
 #endif
   for (int i = 0; i < last_line; i++) {
-    tty_glyph *p = lines[i];
-    lines[i] = 0;
+    tty_glyph *p = lines_[i];
+    lines_[i] = 0;
     tty_glyph *g = 0;
     while (p) {
       tty_glyph *tem = p->next;
@@ -805,89 +810,42 @@ void tty_printer::end_page(int page_length)
       else {
        if (want_horizontal_tabs) {
          for (;;) {
-           int next_tab_pos = ((hpos + TAB_WIDTH) / TAB_WIDTH) * TAB_WIDTH;
+           int next_tab_pos = ((hpos + tab_width) / tab_width) * tab_width;
            if (next_tab_pos > p->hpos)
              break;
-           if (is_continuously_underlining)
-             make_underline(p->w);
-           else if (!use_overstriking_drawing_scheme
-                    && is_underlining) {
-             if (do_sgr_italics)
-               putstring(SGR_NO_ITALIC);
-             else if (do_reverse_video)
-               putstring(SGR_NO_REVERSE);
-             else
-               putstring(SGR_NO_UNDERLINE);
-             is_underlining = false;
-           }
+           // TODO(humm): Should we not take the width of the actual
+           // tab?  The current status works, albeit not with
+           // typewriters: _\b\t is rendered as multiple underlined
+           // cells by less.  We could pass update_attributes the width
+           // the actual tab will have and let it emit multiple
+           // underlines.
+           update_attributes(is_continuously_underlining, is_boldfacing,
+                             curr_fore_idx, curr_back_idx, '\t', p->w);
            putchar('\t');
            hpos = next_tab_pos;
          }
        }
        for (; hpos < p->hpos; hpos++) {
-         if (is_continuously_underlining)
-           make_underline(p->w);
-         else if (!use_overstriking_drawing_scheme && is_underlining) {
-           if (do_sgr_italics)
-             putstring(SGR_NO_ITALIC);
-           else if (do_reverse_video)
-             putstring(SGR_NO_REVERSE);
-           else
-             putstring(SGR_NO_UNDERLINE);
-           is_underlining = false;
-         }
+         update_attributes(is_continuously_underlining, is_boldfacing,
+                           curr_fore_idx, curr_back_idx, ' ', p->w);
          putchar(' ');
        }
       }
       assert(hpos == p->hpos);
       if (p->mode & COLOR_CHANGE) {
-       if (!use_overstriking_drawing_scheme) {
-         if (p->fore_color_idx != curr_fore_idx) {
-           put_color(p->fore_color_idx, 0);
-           curr_fore_idx = p->fore_color_idx;
-         }
-         if (p->back_color_idx != curr_back_idx) {
-           put_color(p->back_color_idx, 1);
-           curr_back_idx = p->back_color_idx;
-         }
-       }
+       // test because we don't have any (c,w) to pass and won't do
+       // colors if those would be used
+       if (!use_overstriking_drawing_scheme)
+         update_attributes(is_underlining, is_boldfacing,
+                           p->fore_color_idx, p->back_color_idx, 0, 0);
        continue;
       }
-      if (p->mode & UNDERLINE_MODE)
-       make_underline(p->w);
-      else if (!use_overstriking_drawing_scheme && is_underlining) {
-       if (do_sgr_italics)
-         putstring(SGR_NO_ITALIC);
-       else if (do_reverse_video)
-         putstring(SGR_NO_REVERSE);
-       else
-         putstring(SGR_NO_UNDERLINE);
-       is_underlining = false;
-      }
-      if (p->mode & BOLD_MODE)
-       make_bold(p->code, p->w);
-      else if (!use_overstriking_drawing_scheme && is_boldfacing) {
-       putstring(SGR_NO_BOLD);
-       is_boldfacing = false;
-      }
-      if (!use_overstriking_drawing_scheme) {
-       if (p->fore_color_idx != curr_fore_idx) {
-         put_color(p->fore_color_idx, 0);
-         curr_fore_idx = p->fore_color_idx;
-       }
-       if (p->back_color_idx != curr_back_idx) {
-         put_color(p->back_color_idx, 1);
-         curr_back_idx = p->back_color_idx;
-       }
-      }
+      update_attributes(p->mode & UNDERLINE_MODE, p->mode & BOLD_MODE,
+                       p->fore_color_idx, p->back_color_idx, p->code, p->w);
       put_char(p->code);
       hpos += p->w / font::hor;
     }
-    if (!use_overstriking_drawing_scheme
-       && (is_boldfacing || is_underlining
-           || curr_fore_idx != DEFAULT_COLOR_IDX
-           || curr_back_idx != DEFAULT_COLOR_IDX))
-      putstring(SGR_DEFAULT);
+    update_attributes(false, false, DEFAULT_COLOR_IDX, DEFAULT_COLOR_IDX, 0, 
0);
     putchar('\n');
   }
   if (want_form_feeds) {
@@ -920,6 +878,22 @@ static void update_options()
     do_underline = want_italics_by_underlining;
   }
   else {
+    // TODO(humm): Do better error handling.
+    int err;
+    setupterm(terminal_name, 1, terminal_name != NULL ? NULL : &err);
+    if (err == 1) {
+      // TODO(humm): Do error handling for the capabilities.  Can they
+      // be null pointers?  Can they be (char*)-1?  Should we fall back
+      // to underline if italic is not available and the like?  Should
+      // we ignore attributes we can't fulfill, or should we abort?
+      use_terminfo = true;
+      sgr_bold = enter_bold_mode;
+      sgr_italic = enter_italics_mode;
+      sgr_underline = enter_underline_mode;
+      sgr_reverse = enter_reverse_mode;
+      sgr_exit_attributes = exit_attribute_mode;
+      tab_width = init_tabs;
+    }
     do_sgr_italics = want_sgr_italics;
     do_reverse_video = want_reverse_video_for_italics;
     bold_underline_mode = BOLD_MODE|UNDERLINE_MODE;
@@ -942,7 +916,7 @@ int main(int argc, char **argv)
     { "version", no_argument, 0, 'v' },
     { NULL, 0, 0, 0 }
   };
-  while ((c = getopt_long(argc, argv, "bBcdfF:hiI:oruUv", long_options, NULL))
+  while ((c = getopt_long(argc, argv, "bBcdfF:hiI:orT:uUv", long_options, 
NULL))
         != EOF)
     switch(c) {
     case 'v':
@@ -998,6 +972,9 @@ int main(int argc, char **argv)
       // Ignore \D commands.
       allow_drawing_commands = false;
       break;
+    case 'T':
+      terminal_name = optarg;
+      break;
     case CHAR_MAX + 1: // --help
       usage(stdout);
       break;
@@ -1021,7 +998,7 @@ int main(int argc, char **argv)
 static void usage(FILE *stream)
 {
   fprintf(stream,
-"usage: %s [-bBcdfhioruU] [-F font-directory] [file ...]\n"
+"usage: %s [-bBcdfhioruU] [-F font-directory] [-T term] [file ...]\n"
 "usage: %s {-v | --version}\n"
 "usage: %s --help\n",
          program_name, program_name, program_name);
-- 
2.40.1




reply via email to

[Prev in Thread] Current Thread [Next in Thread]