Description: This FAQ gives some background and discussion for frequently encountered problems with the ncurses library, the terminal database and applications.
Keywords: ncurses, curses, terminfo, termcap

https://invisible-island.net/ncurses/
Thomas E. Dickey
$Date: 2026/05/17 19:56:25 $

Here is the latest version of this file.

# NCURSES — Frequently Asked Questions (FAQ)

## What is ncurses?

ncurses (new curses, pronounced "enn-curses") started as a freely distributable “clone” of System V Release 4.0 (SVr4) curses. It has outgrown the “clone” description, and now contains many features which are not in SVr4 curses. Curses is a pun on the term “cursor optimization”. It is a library of functions that manage an application's display on character-cell terminals (e.g., VT100).

The name “ncurses” was first used as the name of the curses library in Pavel Curtis's pcurses, dated 1982. It was apparently developed on a 4.3BSD system, at Cornell. Parts of pcurses are readily identifiable in ncurses, including the basics for the terminfo compiler (named `compile` in that package):

- the header filename `ncurses.h`

- the `Caps` file, used to define the terminfo capabilities

- awk scripts `MKcaptab.awk`, `MKnames.awk`

- the library modules used for the terminfo compiler.

While the name of the library itself comes from “pcurses”, it had a different connotation to Curtis. His makefile built `libncurses.a` (normal) and `libdcurses.a` (debugging). In the documentation, Curtis referred to his package as “the new curses” like this, in `changes.ms`:

>                      New Features in Curses and Terminfo

>                                  Pavel Curtis

>          1.  Introduction

>               This  document  describes  new  features that are being
>          added to the Berkeley curses subroutine  package.   It  also
>          describes  the  new  terminfo  database,  which replaces the
>          Berkeley termcap database.  The emphasis is on the new  fea‐
>          tures.

>          2.  New Features in Curses
>          ...
>          2.7.  Mini‐Curses*

>          ───────────
>          *This feature is not supported in the current test
>          release.  It will be implemented in  the  official
>          distribution.

>                                       ‐6‐

>               The  new  curses is bigger than the old one, and has to
>          copy from the current window to an internal screen image for
>          every  call  to refresh().  If the programmer is only inter‐
>          ested in screen output optimization, and does not  want  the
>          windowing  or  input  functions,  an  interface to the lower
>          level routines is available.  This  will  make  the  program
>          somewhat  smaller  and faster.  The interface is a subset of
>          full curses, so that conversion between the  levels  is  not
>          necessary to switch from mini‐curses to full curses.

Rather than being at the start a replacement for AT&T curses, initially it was an extension of BSD curses. Later, supplanting AT&T curses became more important, with different developers.

Besides ncurses, parts of pcurses still survive in recognizable form in Solaris, etc., because the `tic` program from pcurses was used by AT&T (see related discussion). Some misinformation regarding pcurses was provided in a posting to comp.terminals long ago:

>     Mark took “terminfo” to AT&T with him, and it was adopted for UNIX System
>     V Release 2 as a replacement for “termcap” (which was temporarily still
>     supported in SVR2).  UCB, however, stuck with termcap for quite a while
>     (through 4.3BSD at least), merely bringing the termcap manual entry up to
>     date with the SVR2 version of terminfo insofar as possible (I was the
>     editor for the 4.3BSD termcap manual entry).  Pavel Curtis provided his
>     own public-domain implementation of terminfo/curses, but I don't think it
>     really caught on.

## Who wrote ncurses?

- Zeyd Ben-Halim started it from a previous package `pcurses`, written by Pavel Curtis. The first widely-used version (1.8.1 in November 1993) was not much larger than pcurses. It added freely-available examples such as `worm`, and a crude configure mechanism.

- Eric Raymond continued development, apparently starting in late 1993 or early 1994.

- Juergen Pfeifer wrote most of the form and menu libraries. Eric added those libraries to ncurses in August 1995, after I had started working with Eric and Zeyd in March 1995, before ncurses 1.9 was released.

- I've done most of the configuration work, do most of the ongoing development and testing.

- numerous people (more than I know about) contributed fixes.

  For details, see the NEWS file in the source distribution. It accurately reflects contributions since 1.9.9e.

In preparing copyright transfer in 1997, I identified more than 20 contributors based on my software archives.

These individuals were cited in the agreement as having contributed more than 20 lines of code each:

>     Heinz-Ado Arnolds, Jeremy Buhler, Andrey Chernov, J.T. Conklin,
>     Ulrich Drepper, Juergen Ehling, Werner Fleck, Per Foreby, Gerhard
>     Fuernkranz, Anatoly Ivasyuk, Andrew Kuchling, H.J. Lu, Alexander
>     V. Lukyanov, David MacKenzie, Rick Marshall, Hellmuth Michaelis,
>     Tim Mooney, Philippe De Muyter, Eric Newton, Andreas Schwab,
>     Jesse Thilo, Warren Tucker, Peter Wemm.

Four of those made subsequent contributions, but only one exceeding 0.1% of the total (Lukyanov, with 1.3%). As of 2025, almost 290 contributors have been recorded in the changelog (see this page for context).

In addition to Florian La Roche, who agreed to act as maintainer, these were the principal authors of ncurses, for assigning copyright to the Free Software Foundation:

- Zeyd M. Ben-Halim
- Thomas E. Dickey
- Juergen Pfeifer
- Eric S. Raymond

Ben-Halim made no further contributions; Raymond continued for a short time (about 1.8% of the total as of 2025); Pfeifer continued making contributions for about twenty years.

Pavel Curtis' work is in the public domain, hence not needed for copyright assignment. (The `README` file in the ncurses distribution also identifies the authors).

Florian acted as maintainer for about a year. I continued to do the bulk of development, and prepared the 5.0 release. After Florian left unexpectedly (before 5.0), I resumed my pre-4.2 role as the project maintainer.

Occasionally someone says that it is “written by the GNU Project”. That is incorrect:

- The developers and contributors are clearly identified in the NEWS file.

- The AUTHORS file in the sources identifies the primary developers.

- A complete list of contributors runs to several pages (see summary).

- The Free Software Foundation held a copyright on the redistributable work to reduce disputes. It exists as a 501(c)(3) non-profit organization, i.e., a charity. As such, it is prohibited from involvement in politics.

  The GNU Project, on the other hand, is an informal organization which ostensibly promotes the work of the Free Software Foundation.

- None of the major contributors to ncurses appears to be involved with either organization.

See the ncurses license page for more information.

## License issues

- How can it be distributed?
- Is it Free Software or Open Source?
- Is it GPL'd?
- Will it ever be GPL?
- What about the tack program?
- What about the terminfo database?

### How can it be distributed?

The major ncurses developers (exclusive of Pavel Curtis, who put his work in the public domain several years before) early in 1998 assigned their copyright to the Free Software Foundation, which promised to use the following distribution terms for at least five years.

> Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, distribute with modifications, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

> The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

> THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE ABOVE COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

> Except as contained in this notice, the name(s) of the above copyright holders shall not be used in advertising or otherwise to promote the sale, use or other dealings in this Software without prior written authorization.

### Is it Free Software or Open Source?

ncurses is free software. It is not “open source” (refer to the license page).

That term applies to a mixture of proprietary software and quasi-free software, and is being promoted currently by several people for a variety of reasons: some as a compromise (in the pejorative sense) between free software and proprietary, and others to take credit for brokering the release of some proprietary software under less stringent conditions.

By relabeling free software (and revising the order of causes and events), the supporters of “open software” are doing the development community a disservice.

### Is it GPL'd?

Surprisingly, some people cite ncurses as an example of GPL or LGPL. The copyright notice (which is the above-quoted license) appears 577 places in the 5.1 sources, including all of the header files. Presumably therefore, these people have not actually looked at ncurses.

Adding to the confusion, I have seen misleading comments such as this (originally this, but it comes and goes):

> In particular, if you intend to port a proprietary (non-GPL'd) application using Cygwin, you will need the proprietary-use license for the Cygwin library. This is available for purchase; please contact sales@cygnus.com for more information. All other questions should be sent to the project mailing list cygwin@sources.redhat.com.

By omitting some of the facts (equating "non-GPL'd" with “proprietary”), this paragraph stated in terms of ncurses, for example, that I could not work on ncurses on cygwin without buying a license for Cygwin. The same applied to the developers of about half of the contributed software for Cygwin, since not all are GPL'd. There was a better attempt at explaining Cygwin licensing here, but the other page did not use it:

> This means that you can port an Open Source(tm) application to cygwin, and distribute that executable as if it didn't include a copy of libcygwin.a/cygwin1.dll linked into it. Note that this does not apply to the cygwin DLL itself. If you distribute a (possibly modified) version of the DLL you must adhere to the terms of the GPL, i.e. you must provide sources for the cygwin DLL.

Probably more people read the FAQ (and were misled) than read the licensing page.

This type of license, by the way, is often referred to as "MIT-style", referring to the MIT X distribution terms. Before assigning copyright to the FSF (Free Software Foundation), substantial portions of ncurses were copyrighted in this style. The main restriction that affects most people is that the copyright notice must be kept on copies—or portions of the copies. That is not done in this online reference, which documents an older version of ncurses. The translation from manpage to html retains the content, but removes the copyright notice, which one may observe is not permitted. Compare with this (copyright notices are retained in the online content, as you can see in the source-view of the page).

For what it's worth, the agreement which we (original ncurses developers) made with the Free Software Foundation reads in part:

> The Foundation promises that all distribution of the Package, or of any work "based on the Package", that takes place under the control of the Foundation or its agents or assignees, shall be on terms that explicitly and perpetually permit anyone possessing a copy of the work to which the terms apply, and possessing accurate notice of these terms, to redistribute copies of the work to anyone on the same terms. These terms shall not restrict which members of the public copies may be distributed to. These terms shall not require a member of the public to pay any royalty to the Foundation or to anyone else for any permitted use of the work they apply to, or to communicate with the Foundation or its agents in any way either when redistribution is performed or on any other occasion.

As is well known, that precludes relicensing to the GPL in any version, since it would place restrictions on which programs may link to the libraries. That would deprive a substantial fraction of the current user base of the use of subsequent versions of the software. No such restriction exists in the ncurses license.

### Will ncurses ever be GPL?

I have never considered it a possibility (see the preceding section). It would make the package unusable for most of its current user base, because GPL is a more-restrictive license than MIT-X11 or any of the similar BSD licenses.

However, since the FSF holds a copyright to most of the releases published on its website, it is not impossible that someone might publish a version of ncurses relicensed under the GPL. In that case, I would continue development based on the previous version, using the existing license—the one to which I initially agreed. Because I do almost all of the development, and provide the development website, doing that would have little effect on subsequent releases.

The original agreement stated that changes which I made to the source would be copyright by the Free Software Foundation. That clause expired after five years (in 2003). It does require written notice (for instance today is June 25, 2007), so in the event of serious disagreement with the FSF, this webpage satisfies that. It is worth noting that all changes that I have made since the most recent release would be in that event copyright by me.

Moving forward to February 2020, relicensing was a moot issue. However, some issues with FSF (such as this) could best be done by taking ownership of the copyrights. In preparing for releasing ncurses 6.2, I sent mail to FSF advising them that ncurses 6.2 (and all changes since ncurses 6.1) will be copyright by me (same license, of course).

### What about the tack program?

That is not part of ncurses. As a convenience (to reuse library functions that are part of `tic` and `infocmp`), it was distributed with ncurses since before 5.0 (patch date 990417). Beginning with release 1.08 in July 2017, it is able to work with other implementations of curses (although editing a terminal description—done rarely—requires ncurses).

However, `tack` is licensed differently: the GNU General Public License, version 2 (GPLv2).

This confused some packagers, who then labeled ncurses as GPL. Most packagers correct the designation when requested. Some do not. To avoid this confusion, it was removed from the ncurses distribution in 2007, shortly after 5.6 release.

Unlike ncurses, FSF does not have a release-page on its website for tack, and no one has suggested that it was written by the GNU Project. Except for a few (small changes), this was written by Daniel Weaver and me (see AUTHORS file in the source). Its homepage is here.

### What about the terminfo database?

- Copyright and Licensing
- Attribution
- Other Versions

#### Copyright and Licensing

The terminfo database is a special case. Ncurses provides a different version of the `terminfo.src` file originally collected by Eric Raymond. The ncurses file is not maintained by Eric Raymond, since the agreement which transferred control to FSF states:

> We hereby agree that if we have or acquire, or any one of us has or acquires, hereafter any patent or interface copyright or other intellectual property interest dominating the Program (or use of the same), such dominating interest will not be used to undermine the effect of this assignment,

Changes made to this file are (unsurprisingly) copyrighted via the Berne convention. No explicit "Copyright ©" is required. It only requires that the author be identified (and this is done in the history comments at the end of the file):

> (1) In order that the author of a literary or artistic work protected by this Convention shall, in the absence of proof to the contrary, be regarded as such, and consequently be entitled to institute infringement proceedings in the countries of the Union, it shall be sufficient for his name to appear on the work in the usual manner. This paragraph shall be applicable even if this name is a pseudonym, where the pseudonym adopted by the author leaves no doubt as to his identity.

and noting the first comment in the file states that it is maintained as part of ncurses, this applies:

> (3) In the case of anonymous and pseudonymous works, other than those referred to in paragraph (1) above, the publisher whose name appears on the work shall, in the absence of proof to the contrary, be deemed to represent the author, and in this capacity he shall be entitled to protect and enforce the author's rights. The provisions of this paragraph shall cease to apply when the author reveals his identity and establishes his claim to authorship of the work.

Raymond wrote a disclaimer in the `terminfo.src` file which disagrees with some of this. However, Raymond's disclaimer was based on more than one misconception. There is an interesting story about that in another place.

#### Attribution

Occasionally someone in a newsgroup posts a terminfo which has been exported using `infocmp`, saying that it is theirs (and even written by them). Sometimes the claim is true, though more often the data is identical to that from ncurses or a package which includes ncurses. The latter case is interesting.

For instance OpenQM used terminfo entries which were obtained from ncurses using `infocmp`. In discussion, one aspect glossed over was that some of the content was copied not from ncurses itself but from a packager's patch which merged a xterm terminfo which I wrote. Ultimately, the responses from that discussion boiled down to saying that they found it and it's theirs. (The maintainer did agree to add a comment noting the origin of the “public domain” entries).

#### Other Versions

Eric Raymond's website has an old version misleadingly numbered "11.0". It actually is much older than ncurses's terminfo (whose major version I have left as “10”).

The content of "11.0" is derived from ncurses 5.0. It makes more than one change, but most are cosmetic (e.g., reordering the entries within the file, adding about 300 lines of comments—in an 18,655 line file—to make the reordering look nicer). None of the added comments are useful.

It also modifies the changelog from ncurses to make it appear that people who reported problems to me were the ones who did the subsequent investigation and patches. He had done the same thing prior to ncurses 4.2, for several months in 1997 and 1998, copying changes from ncurses development, and then later “revising” the change history. (I later restored that portion of the changelog).

The last version (11.0.1) copies one of my fixes from ncurses, (prompted by a bug-report by Tijs Michels on the rxvt-workers mailing list in January 2000, in response to ESR's announcement of "11.0.0"). In the mailing list, I pointed out the reason for my change. My original change comment in 1997 said

> # 10.1.16 (Sat Dec 13 19:41:59 EST 1997)
> # * remove hpa/vpa from rxvt, which implements them incorrectly.
> # * add sgr0 for rxvt.
> # * remove bogus smacs/rmacs from EMX descriptions.

GNU termcap 1.3.1 distributes "11.0.1", generated using ncurses' tic program. Disregarding the issue that the file is old and faulty, the reason for generating the file is that ESR's website does not provide a version which resolves all but the last "`tc=`" inclusions.

## How big is ncurses?

- Growth of the feature set
- Types of library users
- Relationship with vi
- Applications miscited as library users

The answer depends on why you are asking. Some of the reasons for asking include

- does it have some given feature.

- will it fit in some limited-size embedded application,

### Growth of the feature set

As noted, ncurses began as a clone of SVr4 curses (up til around 1995). Later, The Open Group began a specification of curses (XSI Curses), which is now known as X/Open Curses. That provided for "wide-characters", such as Unicode, although at that point Unicode was not the obvious answer.

There were a few functions (such as `attr_get`) which were added into the ncurses library in anticipation of XSI Curses. However, I chose to implement the wide-character support using a different library name, “ncursesw”. Doing that allowed me to maintain compatibility with applications that used the existing “ncurses” library.

Given that, the “ncurses” library would be comparable to a SVr4 implementation (such as Solaris, IRIX64 or HPUX), while the “ncursesw” library would be comparable to one of the XPG4 implementations (Tru64 being the notable implementation). The ncurses (and ncursesw) library provide some extended functions not found in SVr4/XPG4. A few implementations (PDCurses and NetBSD curses) provide some of these extensions.

Later, I added functions to support simple threaded applications, and Juergen Pfeifer extended that. Again, to maintain compatibility, this is normally built as a a new library name, “ncursest” or “ncurseswt”. First noted in mid-2011, at this time (mid-2020), there is no other implementation of these features.

The ncurses and ncursesw libraries are reasonably source-compatible. That is, an application written for “ncurses” will build with “ncursesw”. But it will behave differently in response to your locale settings. (Some distributors, who do not care about the differences, have chosen to merge the names together as “ncurses”).

A few applications require changes to use “ncursest”, since internal details of the `WINDOW` object are not directly visible in the latter. However, the “ncurses” library has macros and functions which address this area.

Every implementation of curses uses both macros and functions to provide their features. ncurses follows the XPG4 convention where all macros (except for those such as `getyx` which must be implemented solely as macros) are also implemented as functions.

Here are counts comparing ncurses 5.9 with other implementations:

> Implementation | Macros | Public symbols
> --- | --- | ---
> ncurseswt (sp-funcs) | 219 | 541
> ncursest (sp-funcs) | 153 | 439
> ncurseswt | 219 | 429
> ncursest | 153 | 332
> ncursesw | 219 | 454
> ncurses | 153 | 357
> Tru64 5.1 | 228 | 481
> Solaris 10 XPG4 | 180 | 374
> Solaris 10 SVr4 | 199 | 422
> IRIX64 6.5 | 195 | 394
> HPUX 11.23 XPG4 | 162 | 472
> HPUX 10.20 XPG4 | 172 | 468
> HPUX 10.20 SVr3 | 197 | 323
> AIX 7.1 | 207 | 480
> PDCurses 3.4 | 9 | 364
> NetBSD 5.1 | 86 | 367

In each case, internal functions are not counted.

The Unix implementations include undocumented features for compatibility with older curses implementations that are not provided by ncurses.

Both PDCurses and NetBSD curses contain functions not counted here because they are not relevant to a comparison with SVr4/XPG4 curses. For example, PDCurses in X11 contains functions for initializing the X window. On the other hand, relevant extensions such as PDCurses' version of `wresize` are counted.

### Types of library users

PDCurses on the other hand does not include the functions used to obtain terminfo information. That does not prevent it from being a curses implementation. X/Open Curses' documentation treats those separately, allowing for the possibility of curses implementations without terminfo (or termcap either for that matter).

That raises another issue: what types of interfaces do curses libraries (and ncurses in particular) support?

ncurses includes the conventional curses interfaces, with extensions (new functions) in each interface. The interfaces are:

- form, menu: upper-level libraries provided in a few systems such as SCO and Solaris.
- panel: an upper-level library which should have been standarized as part of the curses library.
  Again (outside of ncurses), it is provided by SCO and Solaris.
- curses: the higher-level interface used by all curses applications.
- terminfo: a lower-level interface used by some applications.
- termcap: a lower-level interface used by some applications.

Curiously, NetBSD provided variants of the form and menu libraries in late 1999, but lacked a panel library until 2015 (see source). Conversely, PDCurses provides a panel library but lacks the form and menu libraries. Because NetBSD uses opaque structures, it is difficult to write portable applications using their form and menu libraries. The ncurses-examples have some workarounds for this to allow them to compile with NetBSD curses. One might have better luck with PDCurses' panel library, which has the same ancestor as ncurses' panel library.

The lower-level interfaces rely upon the application (rather than the library) to decide how to put characters on the display. That is referred to as “optimization”, e.g., in the documentation:

> The ncurses library routines give the user a terminal-independent method of updating character screens with reasonable optimization.

Most applications made the transition to using the curses interface long ago. There are some applications which use one of the lower-level interfaces. In some cases there are technical reasons for this. Inertia is more often the reason.

Here are some examples of well-known applications which use curses:

- lynx
  A curses application from the beginning, lynx can be built with any version of curses, including PDCurses and VMS curses.

- nvi
  Keith Bostic introduced nvi in 4.4BSD, revised it for 4.4BSDLite in 1994. At that point, it was using curses (preferably System5 curses). Lacking that, it had a bundled copy of 4.4BSD curses, which sufficed. Bostic's interest in ncurses stemmed from his desire to eliminate the bundled 4.4BSD curses, and he was helpful in many ways, both technical (with bug reports) and otherwise.

- tin
  Originally in K&R C using termcap, I modified it to use curses. Most of the subsequent work to handle wide-characters was done by others.

Widely-used termcap applications include these:

- less
  Several `less` features are undocumented. One of these features is the use of environment variables to override termcap capabilities. At startup, when `less` retrieves each termcap capability, it first checks for an environment variable (named by prefixing the capability name with “`LESS_TERMCAP_`”) and uses the environment variable's value if it exists. That appeared in `less` between versions 321 and 330 (July–October 1996).

- screen
  The `screen` program has had more impact on ncurses development than the other applications because there were features which `screen`'s developers wanted for compatibility with “real” (runtime adjustments of `sgr0` to imitate termcap's corresponding `me` in 2001 and using padding in `delay_output` rather than time-delays in 1999). The latter was marked as a problem in screen's source code; it took several years for that to be addressed (see related discussion).

- w3m
  While `w3m` is a termcap application, it includes source code that makes it pretend to use curses. For instance, it includes a module terms.c whose header comment is An original curses library for EUC-kanji by Akinori ITO, December 1989. This module does not do optimization as a curses library would do, but uses a simpler approach (which works well with multibyte characters). As explained by the developer:

  > By the way, w3m doesn't use UNIX standard regexp library and curses library. It is because I want to use Japanese. When I wrote fm, there were no free regexp/curses libraries that can treat Japanese. Now both libraries are available and they looks faster than w3m code.

  What complicates the program is that some of its symbols duplicate those in the curses library with which it is linked (see related discussion).

- vim
  Vim's developers provide their own termcap definitions, just in case there is nothing good enough on the system, and provide features for overriding the system's termcap capabilities even when using the system definition as a starting point. Because of this, vim has had little impact on ncurses development; the change-log does not mention vim. On the other hand, unlike `screen`, the source-code for vim still contains a comment about a bug in ncurses which was addressed in late 1997, before ncurses 4.2 was released.

Applications which use only terminfo are less well-known. For example, there are

- ncurses-examples (e.g., demo_terminfo, list_keys and test_sgr)
- tack
- tmux

Because the terminfo and termcap programming interfaces are similar, it is trivial to make an application build with terminfo if it was originally written to use termcap. These are done using a table for the capabilities, taking advantage of the fact that all of the conventional termcap capabilities are associated with terminfo capabilities. Here are a few examples:

- vile
- xterm

Going the other way (starting with a terminfo application and making it work with termcap) is not necessarily simple:

- The terminfo interface provides a data structure `TERMTYPE` holding all of the terminal's information which eliminates the need for calls to the tigetstr, tigetnum and tigetflag functions. If an application (such as tack) is written to use that, it is difficult to make it use termcap.

- Additionally, since 1999, ncurses provides extended capabilities in its terminal database which are not necessarily visible to termcap applications. XTerm, in its `tcapFunctionKeys` feature uses these capabilities; gnome-terminal in its analogous termcap interface (removed in 2014) could not.

  The user_caps(5) manual page goes into greater detail.

Because of these differences, it is best to speak of termcap-applications, terminfo-applications and curses-applications. Curses-applications may use terminfo functions, but the reverse is not true. Given the terminfo interface, there is no reason for a curses-application to use the termcap interface.

An easy way to distinguish between the three types of applications is to see what library calls they make:

- curses – initscr or newterm
- terminfo – setupterm
- termcap – tgetent

Even this categorization is simplified:

- Some curses applications (such as nvi) switch between full-screen and normal modes of operation, e.g., to support the “open mode” of vi. To accomplish that, nvi uses lower-level calls at times, e.g., to erase characters.

- nvi (and dialog) treat xterm's alternate screen feature specially, using low-level workarounds to disable the feature as they switch to/from full-screen mode.

- nvi (and vile, using its curses driver) do not use the curses library's input function wgetch. That is because vi treats the escape character specially. Consequently, the curses decoding of function- and special-keys is not usable by vi-like programs.

Nothwithstanding their use of low-level calls, these are curses applications because they use the library to update the display. Non-curses (termcap and terminfo) programs use only the terminal database. Applications which do their own display optimization (such as vim) are not curses applications.

If someone simply categorizes any application which is linked to (or uses in some sense) the ncurses library as an ncurses application, that rapidly leads to absurd conclusions, as for example in Debian #265631, where a developer insisted that a bug (apparently in a different library) was a bug in ncurses because the application in question used the gpm library. In other cases, e.g., lists made by nondevelopers based on package dependencies, this sort of misinformation is commonplace.

### Relationship with vi

Not all implementations of vi are curses applications. In fact, considering it carefully, most are not.

One likely objection to that statement is the generally accepted notion that Ken Arnold “took” functions from Bill Joy's vi to make his library. For instance, in the preface to UNIX Curses Explained, Goodheart said (in 1991):

> It all started in the late 1970s when Bill Joy, in writing his editor ex (probably more famous by the name vi nowadays), wrote a set of routines which read a terminal capability database. The database, then named termcap, generally described how to manipulate individual terminals and what they where capable of. The routines he created, which accessed the termcap database, implemented optimal cursor movement.

> Kenneth C.R.C. Arnold took these routines almost without changes and derived from them what is known today as the curses package.

People tend to refer to the second paragraph without noticing the first one. The “where” versus “were” typographical error in the first paragraph is an error by the publisher. The last sentence of the first paragraph is an error by the author: termcap does not, never did do that.

Optimal cursor movement (cursor optimization) in ex was done in the remainder of the application. The termcap functions were readily reusable; the remainder was not. Arnold added to Joy's original idea by making the library reusable.

The Unix Heritage Society has copies of 3BSD, 4.2BSD, 4.3BSD (multiple). Using those, one can make useful comparisons :

- ex_vis.h file from ex in the 4.2BSD distribution
- curses.h from curses library in the same distribution.

Joy's header file is littered with separate variables. Arnold's header file organizes those into structures, notably `WINDOW`. The `vtube` array in the former corresponds to the bulk of the storage used by `WINDOW`. In the same way, Arnold recognized useful aspects of terminal manipulation scattered through ex, and organized those into a library which improved on the original design. Aside from `beep`, there is no straightforward mapping between the functions in the two programs.

Traditional vi, however, does not use curses. With the release of 4.2BSD, it lost its private copies of the termcap functions, and, in the main branch of development, at AT&T, became a terminfo application. With 4.3BSD, the termcap-based vi (and derived code such as “heirloom vi”) was no longer the main line of development. Bostic's nvi was a re-implementation (based on elvis), done specifically to disentangle the BSD project from AT&T source code.

Switching to terminfo was simple. Switching back would be hard, since the AT&T vi uses the `TERMTYPE` structure for accessing the terminal capabilities. AIX, HPUX, IRIX64, Solaris all use the AT&T-derived vi.

### Applications miscited as library users

Here is a short list of applications commonly confused as users of curses, terminfo or termcap. The reason for the confusion is that they use the `TERM` environment variable, and some give a little attention to the terminal database. But the essential approach taken by their developers is to hard-code their assumptions about the terminals.

- The “S-Lang” (more commonly just slang) library may use the termcap file, or its own (subset of ncurses) interface to the terminfo database. However, it overrides the terminfo/termcap data with its author's assumptions which can differ radically from your actual terminal capabilities.

- ELinks (and its ancestors links, links2), generically referred to as (e)links(2) assumes everything is some variation of Linux console, xterm or color-vt100. The Text Terminal HOWTO provides some misinformation on this topic

  > But links2 and elinks will work with any terminal by classifying the type as dumb like the first terminals.

  Rather, (e)links(2) simply uses VT100 escape sequences if it notices that `TERM` is set to dumb.

- URWid (see for example are there any tree libraries/widgets for (n)curses). According to its documentation:

  > If you don’t specify a display module, the default main loop will use raw_display.Screen by default.

  and goes on to mention that when using (n)curses, there is no support for 88- or 256-colors or mouse support. The point which URWid's developers are making is that the curses module is there solely to provide justification for the hard-coded “raw display” module.

- Linux setterm, which knows many of the Linux escape sequences documents documented in console_codes. However, of its 40 command-line options, 60% — all of those which are frequently used — duplicate `tput`, `reset`, or `tabs`. The others are rarely used, Linux-specific.

- GNU ls and dircolors. The latter program has a list of `TERM` values which it assumes all support color, using `bce` (back color erase), including “vt100” (which never supported color).

  For other comments, see

  - Solarized colorscheme in fbterm?
  - How to remove dir background in `ls -color` output

## Where is ncurses used?

- Generally workable systems
- non-Linux systems
- Other systems: VMS
- Examples of ncurses programs

ncurses should build and work on any POSIX platform. It also works on some platforms that are non-POSIX. However, it requires these POSIX features (available on all supported platforms):

- a standard C compiler (c89 or later)

- a POSIX shell (which requires a workaround for Solaris' obsolete shell—see the 6.0 release notes).

### Generally workable systems

Current development is focused on the wide-curses configuration (ncursesw). These platforms are known to work:

- BSD variants:
  - FreeBSD 12-13
  - OpenBSD 6-7
  - NetBSD 8-10
- Linux-based systems
  - Arch Linux
  - Debian 10-12, and testing
  - Fedora 38-41 and rawhide, CentOS 6-9
  - Mageia 7-9

The normal (8-bit character) configuration is known to work on the same platforms. I've also built these in preparation for the current release:

- AIX 7, 6, 5.3
- HPUX 11.31, 11.23
- MacOS 13, 14
- Solaris 11, 10
- Windows 11, 10, 8, 7, using Cygwin, MinGW and MSYS2.

Previous releases listed other platforms (or versions) which are no longer available for development and testing, e.g., IRIX64, SCO OpenServer, SunOS 4, Tru64. Most of those probably work as well, but keep in mind that because they are defunct, only minor changes would be considered in bug reports.

### non-Linux systems

That is a summary of the recent work which I have done. Others package ncurses and provide it either as the system curses library, or as an add-on. Some people assume that ncurses is a “Linux” program. That is incorrect. Since half of my users are on non-Linux systems, here are some notes:

- FreeBSD and OpenBSD use ncurses as the system curses library.

  Both of those systems (FreeBSD for termcap until 2021, OpenBSD for terminfo until 2015) used source-only entries in their respective hashed system terminal databases. Since 2006, ncurses supports an alternate configuration, storing compiled (binary) entries in its hashed database, to improve runtime performance.

  - FreeBSD's system curses library uses the termcap reader from ncurses. The base system's terminal database is referred to as “termcap.db” but is actually an ncurses terminfo hashed database.

    Until 2021 (see commit), the ncurses utility programs were not used with FreeBSD's system curses (including tabs and tput— but see discussion in the manual page). The add-on ncurses port provides a terminfo database, along with the ncurses utility programs. Originally that used a conventional directory-tree configuration, but changed in 2013 to use ncurses' hashed-database feature. Several years later, FreeBSD changed back to the directory-tree to eliminate problems with some packages, e.g,. this.

  - OpenBSD, on the other hand, used to use its own terminfo reader for a hashed database. That was discarded late in 2015, to use ncurses.

- NetBSD and Solaris 11 use ncurses' terminal database, with their different implementations of curses.

  NetBSD provides an add-on package for the ncurses libraries and utilities. Although NetBSD developers prefer to use their own version of the curses library, as of September 2023, slightly less than half of the packages whose build script mentions curses specify ncurses (189 of 394).

  Solaris installs ncurses for use by several programs including bash, cmake, gdb, less, lftp, lynx, mutt, nano, python (multiple versions), ruby, tmux, vim, xterm, and zsh.

- As of January 2020, MacOS and OpenBSD provided ncurses 5.7 (from 2008) for their system curses library. A few years later, that is still the same, but there are some hints that might change.

  Due to its age, ncurses 5.7 may not work as expected. For instance, the command `tput ed` was seen to not work with MacOS. Additionally, 256-colors and direct-colors are not supported by the ncurses library (done in ncurses 6.0 and 6.1, respectively), and some extensions are known to malfunction even when using just the low-level terminfo or termcap interfaces (see ncurses 6.2 release notes).

  - According to recent (September 2023) discussion with OpenBSD developers, they plan to upgrade ncurses in OpenBSD 7.4, while enabling the ncurses 6.x enhancements.

  - For MacOS, the story is less clear.

    Recent updates in Apple's Git repository have been aimed at some of the ncurses updates in the terminfo functions (see the “ncurses-61” branch which applies the changes for tiparm_s). That could help, but being fifteen years out of date is a serious handicap.

    In July 2023, the MacOS terminfo database was updated. A subsequent bug report tmux #3677 showed that the entry for xterm-256color had errors. Because that sort of thing could happen if one used the ncurses 5.7 utilities to compile a terminfo source from ncurses 6.2 or later, I mention this problem on the terminal database section of the ncurses home page.

- Add-on packages (or “ports”) for recent releases are available for all of the BSDs, except for OpenBSD:

  - FreeBSD ports
  - MacPorts and brew
  - pkgsrc, for NetBSD and others.

  Newer versions of ncurses also work with OpenBSD,
  but you must configure and compile it yourself (see discussion).

- Solaris has a component for ncurses, which is a dependency of several other components, such as less, python and vim.

### Other systems: VMS

While working on tin in 2000, I noticed that VMS curses is essentially 4.3BSD curses (no color, no video highlights beyond standout, no locale support hence no support for wide-characters). There is no working port of ncurses to VMS.

A defunct port of ncurses associated with GNV is mentioned here (source in Mercurial):

- Does VMS curses support colour ? on comp.os.vms (June 2017)
- ncurses 5.9 port to OpenVMS (2013-08-21)

  >     The current state is that this that it compiles and links. It runs but has errors.

- ncurses - New curses library. (2009-10-08)
  Lists several issues which had to be addressed in a port, about half were specific to ncurses.

### Examples of ncurses programs

The ncurses distribution only includes programs that must be maintained with it, since they rely on internal details of the library.

Part of the ncurses distribution (the test/demo ncurses-examples) are designed to work with other versions of curses, to help with comparisons.

The release announcements list examples of the different types of library users (e.g., in Applications using ncurses).

A few of those are special, because others used them as examples of ncurses usage, leading to direct involvement in improving their use of ncurses:

- cdk Curses Development Kit (a library of widgets)
- dialog Script-driven curses widgets

## What is the latest version?

The current stable version is 6.4 20221231, available from the ncurses homepage:

> HTTP: ncurses.tar.gz (mirror)

> Local: ncurses.tar.gz

I also maintain development patches toward the next release. See the NEWS file for changes.

> HTTP: https://invisible-mirror.net/archives/ncurses/6.4/ (mirror)

> Local: /archives/ncurses/6.3/

After announcing a new patch, I provide the source in an alternate form as described here:

> ncurses-snapshots

## Official releases

There have been a number of releases of ncurses. Some are available on CDROM (beginning with 1.9.4), and are archived on various ftp servers. If you are downloading, however, the older versions are of limited interest except for software testers.

- 6.5 (30 December 2025). This consolidates the MinGW and Windows terminal drivers.

- 6.5 (27 April 2024). This is a bug-fix release (improved terminfo library interface, and an optional feature for serial terminals).

- 6.4 (31 December 2022). This is a bug-fix release (some feature improvements, but no new features).

- 6.3 (21 October 2021). This corrects a few problems which interfered with portability. It also adds a new console I/O driver for Windows Terminal, and a script to make it easy for OpenBSD users to upgrade their system's ncurses libraries and utilities.

- 6.2 (12 February 2020). This corrects two problems in tic which interfered with extending the terminal database. It also improves checking for mis-typed user-defined capabilities in the terminal database.

- 6.1 (27 January 2018). This improves integration among the command-line utilities (tput, tset, clear). It also extends the range of numeric capabilities.

- 6.0 (8 August 2015). This updates the ABI to support 256-colors, as well as improving termcap compatibility, and the MinGW port.

- 5.9 (4 April 2011). This fixes a regression in `newwin`, and improves configurability/portability of the Ada95 binding when built as a separate tree. (26 February 2011). This extends support for threaded applications by providing a new API which eliminates the need for a global screen-pointer. It also introduces a port to Windows using MinGW, as noted in the 5.8 announcement.

- 5.7 (2 November 2008). This provides rudimentary support for threaded applications. It also distributes `tack` separately.

- 5.6 (17 December 2006). This supports hashed database for the terminal descriptions. It also improves support for magic cookies.

- 5.5 (10 October 2005). This improves support for wide- and multibyte characters, modifies the form- and menu-libraries to work with multibyte characters. It also improves support for cross-compiling.

- 5.4 (8 February 2004). This improves support for wide- and multibyte characters, implements the remaining parts of the X/Open Curses interface. It also improves support for termcap.

- 5.3 (12 October 2002). This provides support for wide- and multibyte characters, implements most of the corresponding X/Open Curses interface. It also improves support for termcap.

- 5.2 (21 October 2000). This provides better support for termcap, fixes for the manpage and shared library configurations, and improved checks for corrupt terminfo database.

- 5.1 (8 July 2000). This provides better support for termcap as well as implementing new extensions for colors.

- 5.0 (23 October 1999). This aligns interfaces to match version 2 of the X/Open Curses Single Unix specification from 1997. It also provides better termcap support, and termcap-like features such as user-defined terminal capabilities.

- 4.2 (2 March 1998). This implements C++ bindings for the library, as well as extensions to support runtime definition of keycodes.

- 4.1 (16 May 1997). This release features support for GPM (mouse on Linux console), and adds an extension for default colors.

- 4.0 (24 December 1996). A change in version numbering addresses a problem exposed by David Engel's `ld.so.1.8.5` program for Linux.

- 1.9.9g (1 December 1996).

- 1.9.9e is broken. A last-minute/untested change causes forms and menus to not refresh. Foreground/background colors are combined incorrectly, working properly only on a black background.

- 1.9.8a (ok)

- 1.9.7a (ok)

- 1.9.4 is the oldest version that you should consider installing. It came with Slackware 3.0; earlier releases had a number of problems, including incompatible terminal descriptions.

## Known/Frequent problems

- Building and Installing NCURSES
  - How do I run the test-programs?
  - How do I apply patches?
  - Where are the patches?
  - The terminfo database is big—do I need all of that?
  - Do I really need a terminfo database?
  - Which terminfo database do I need?
  - Is ncurses terminfo compatible with my system?
  - Is the ncurses library compatible with my system?
  - Problems with remote shells
  - Problems with Cross-Compiling
- Configuring NCURSES
  - Do I need all of those programs and libraries?
  - Do I need the C++ binding?
  - Why does make menuconfig fail?
  - Problem building with gcc 2.96.x
  - Problem building C++ interface with gcc 3.x
  - Testing for Memory Leaks
- Customizing NCURSES
  - How do I set up a private terminfo database?
  - My terminal is not recognized
  - Why use terminfo instead of extensible termcap?
  - What implementations of terminfo are extended?
- Making NCURSES Fast
  - Why does my program scroll slowly?
  - Why does VT100 refresh slowly?
- Making Color Work
  - How do I get color with VT100?
  - My terminal doesn't recognize color
  - My terminal shows some uncolored spaces
  - My xterm program doesn't recognize color
  - Why doesn't ncurses use `$COLORTERM`?
  - Why not just use TERM set to "xterm-color"?
  - Why not just use TERM set to “xterm”?
  - Why not make “xterm” equated to “xterm-256color”?
  - Why only 16 (or 256) colors?
  - Ncurses resets my colors to white/black
  - Why are red/blue interchanged?
- Other Display Problems
  - Line-drawing characters come out as x's and q's
  - Line-drawing characters come out as Latin-1 characters
  - Line-drawing characters do not appear
  - Why does my cursor blink in Emacs?
  - Why does (fill in the blank) happen when I use two threads?
- Keyboard Problems
  - My cursor keys do not work
  - Alt-keys do not work in bash
  - My home/end keys do not work
  - How can I use shift- or control-modifiers?
  - How can I see what my keyboard sends?
- Using Hardware (Real) Terminals
  - Why does reset log me out?
  - Why do I get trash on the screen?
- Interaction with Other Programs
  - Redirecting I/O to/from a Curses application
  - What about readline?
  - Problems with Output Buffering
- Mice and Windows
  - I can't cut/paste in xterm
  - Handling `SIGWINCH` (resize events)
  - Linking with GPM (Linux console mouse library)
- Problems with Packages
  - Comments on packages
  - Ncurses 4/4.2/5.0
  - rxvt's `$COLORFGBG` variable
  - Where is rxvt-unicode?

### Building and Installing NCURSES

#### How do I run the test-programs?

You must first install the terminfo data (i.e., "make install.data").

On many systems (those that have a SVr4 curses installed) you can run the test programs using the vendor's terminfo database (e.g., Solaris, IRIX, HP-UX) by setting the TERMINFO variable to point to that instead.

#### How do I apply patches?

See also How are patches organized?

I name development patches after the base release, with the patch date originally (in 1996) in the form yymmdd and starting with the year 2000 yyyymmdd.

- you need patch 2.1 (originally, I believe, in the X distribution, but also from GNU now, e.g., ftp.gnu.org). Version 2.5 offers some advantages (handles lines wider than 1024 characters), but introduces new bugs (its name resolution algorithm gets more easily confused by duplicate names in the tree). The interim versions (2.2, 2.3, 2.4) are unacceptable.

- you also need gzip 1.2.4, since both the base release and the patches are gzip'd.

- Assuming you have all of the patches and the 4.2 tar.gz file in the same directory and are running in Bourne shell:

  > zcat ncurses-4.2.tar.gz |tar xf -
  > cd ncurses-4.2
  > for n in ../ncurses-4.2-*.gz ; do zcat $n | patch -p1 ; done

#### Where are the patches?

Development patches (and a rollup patch updated periodically) are available for download:

> HTTP: https://invisible-island.net/archives/ncurses/6.4/

> HTTP: https://invisible-mirror.net/archives/ncurses/6.4/

Look for a file named something like "`patch-6.4-yyyymmdd.sh.gz`" The "yyyymmdd" part corresponds to the patch-date.

After providing a rollup patch, I remove the development patches to reduce clutter. Beginning in May 2013, I modified the process to provide all of the development patches since the release in “dev-patches.zip”.

There are also a few rollup patches between releases:

Download:

- patches
- patch-4.2-5.0.sh
- patch-5.0-5.1.sh
- patch-5.1-5.2.sh
- patch-5.2-5.3.sh.gz
- patch-5.3-5.4.sh.gz
- patch-5.4-5.5.sh
- patch-5.5-5.6.sh.gz
- patch-5.6-5.7.sh.gz
- patch-5.7-5.8.sh.gz
- patch-5.8-5.9.sh.gz
- patch-6.0-20150808.sh.gz
- patch-6.1-20180127.sh.gz
- patch-6.2-20200212.sh.gz
- patch-6.3-20211021.sh.gz

The rollup patches include all patches through the cited version. You must apply them to the base release, e.g.,

> zcat ncurses-4.1.tar.gz |tar xf -
> cd ncurses-4.1
> sh ../patch-4.1-4.2.sh

I have tested the rollup patches with patch 2.1 and 2.5, adjusting for their respective limitations.

#### The terminfo database is big—do I need all of that?

Not at all. You can load a subset of the terminfo database. I use a variant of this script to load the terminal descriptions that I need on my machine:

> #!/bin/sh
> # uses the -e switch on tic to selectively load descriptions that are
> # interesting for my testing.
> if test -f terminfo.src ; then
> TMP=/tmp/load$$
> trap "rm -f $TMP" 0 1 2 5 15
> tic -s -1 -I -e'
> ansi, ansi-m, color_xterm, ecma+color,
> klone+acs, klone+color, klone+sgr, klone+sgr-dumb,
> linux, pcansi-m, rxvt, vt52,
> vt100, vt102, vt220, xterm' terminfo.src >$TMP
> tic -s $TMP
> else
> echo 'oops'
> exit 1
> fi

#### Do I really need a terminfo database?

You could compile-in fallback definitions for the most commonly used terminal types. To do this, you must already have `infocmp` installed (note that ncurses 5.0 infocmp's support for fallback descriptions is done differently from ncurses 4.2).

But fallback definitions are really only useful in embedded applications, where no external files are wanted.

#### Which terminfo database do I need?

The most reliable terminfo database is that distributed with ncurses 5.0, or via followup development patches. The original process of incorporating terminal descriptions from various sources corrects some errors in the originals, but introduces others (either translation errors, or misconceptions). Besides working to resolve these, from time to time we incorporate new sources.

As noted in 29 February 2004, the terminfo database at https://www.catb.org/~esr/terminfo/ does not appear to be actively maintained. Since the release of ncurses 5.0 in late 1999, there are numerous fixes which are not in that database.

As of January 2012, this is still true. A check with

> infocmp -x -F termtypes.master terminfo.src

reports that there are 1807 differences for the entries which the two have in common, as well as 325 entries not in the “master” terminfo database.

Here are links to current versions:

- terminfo.src.gz
- termcap.src.gz

If you choose to not install the ncurses terminfo database, we have found that the SVr4 systems (Solaris, IRIX 6, OpenServer and HP-UX 10) work well enough for many purposes. Other systems either are not binary compatible, are incomplete, or contain more errors than either of the choices mentioned. Some that are not binary compatible can be accommodated by configuring ncurses to use the native terminfo format. These include AIX, HP-UX 11, Tru64 and U/Win.

#### Is ncurses terminfo compatible with my system?

Usually.

Terminfo is compiled into binary form, with booleans, numbers and strings in arrays. As long as the array items line up, and the headers (that tell how long the arrays are) are compatible, ncurses and your vendor's system can each use the same terminfo database. Older sytems (e.g,. those based on SVr3) implement a subset of the SVr4 terminfo. For example, HP-UX 9 is “compatible” up to the entries that would describe graphic (box) characters. There it diverges.

Other systems (e.g., Digital Unix 4.x and the older AIX 3.2.5) use different formats and are not compatible.

But those are (very) old systems. If you are not running a computer museum, you may not even recognize the names of these systems.

Even for very old systems, however, terminfo source is compatible and can be compiled using the appropriate tool (usually tic). Some terminfo descriptions may produce warnings (e.g., the memu/meml capabilities in the standard xterm distribution), but the tools compile what they recognize and warn about the rest.

The ncurses tic program recognizes a wider range of input than other terminfo compilers, including extensions coordinated with infocmp that make it easier to use:

- compile descriptions that use the long names that “infocmp -L” produces.

- the “infocmp -f” option formats complex expressions into indented format. These are usable with the standard SVr4 tic program, though not with ncurses 4.0 and below due to a bug.

More important, ncurses tic allows new terminal capabilities to be defined, by the `-x` option. Rather than warning about unrecognized capabilities and (otherwise) ignoring them, ncurses tic will add those to the end of the compiled terminfo file. Those additions (referred to as user-defined capabilities) are hidden from the older SVr4 tic programs because they see only the part described by the file's header.

The older SVr4 tic, of course, is unchanging. Development (and maintenance) stopped long ago. But ncurses development is still (as of 2020) ongoing. Occasionally some bug is found which affects the terminal database:

- ncurses 5.7 fixed a case where tic could have an infinite loop if it encountered a cancelled user-defined capability.
- ncurses 6.2 fixed a case where forward-references to a user-defined capability, e.g., via a “use=” clause, were mishandled.

In each case, the tool was improved, but older versions cannot handle the newer terminfo source. If you must use an older version of ncurses, use the terminfo source which was distributed with that version of ncurses.

If you are using ncurses terminfo with another implementation of tic, the advice is different:

- ncurses 6.1 introduced support for large number capabilities, e.g., for more than 32767 color pairs. Other implementations generally treated out-of-range values as zero. This was addressed two years later in NetBSD's tic program, which may be in NetBSD 10. As of June 2020, the current release is NetBSD 9.
- NetBSD's tic program is known to evaluate cancelled capabilities differently from SVr4 and ncurses.

#### Is the ncurses library compatible with my system?

Yes/no.
Source compatible yes, binary compatible no.

You cannot simply replace your existing curses or termcap library with ncurses unless you are prepared to recompile applications that use the curses or termcap library (e.g., `vi`, `telnet`).

For systems using the Linux kernel, that is feasible. But not Solaris or other proprietary systems. For those, I recommend configuring with the `--disable-overwrite` option. This directs the configure script to install the library so you would link it as `-lncurses`, not adding a symbolic link to make it link as `-lcurses`.

The `--disable-overwrite` option also installs the header files such as `curses.h` in a subdirectory, e.g., `/usr/local/include/ncurses/curses.h`, thereby avoiding a (mis)feature of recent versions of `gcc` which look first in `/usr/local/include` for header files. Since the vendor's compilers do not do this, a common problem results: compiling with `/usr/include/curses.h` and linking with `/usr/local/lib/libcurses.a`.

Starting with ncurses 5.3, the behavior for this option changed. If you do not install into `/usr`, the configure script will assume you do not wish to overwrite the existing version of curses. Configure scripts which do not check for ncurses headers in both locations are incorrect anyway. They can be accommodated by setting the `$CPPFLAGS` environment variable, e.g.,

> setenv CPPFLAGS "-I/usr/local/include/ncurses"

#### Problems with remote shells

Some users notice that remote machines do not have the same set of terminal descriptions as their local machine. Running a remote shell on those machines can be a problem because typical `ssh` configurations export the `TERM` variable to the remote machine.

Developers who work on multiple machines should be used to this problem. It is not new: the various operating systems (Unix, BSDs, MacOS and those using the ncurses terminal database) have different features, different versions.

One interesting quirk is using the `screen` program. The manual page notes:

> When screen tries to figure out a terminal name for itself, it first looks for an entry named "screen.<term>", where <term> is the contents of your $TERM variable. If no such entry exists, screen tries “screen” (or "screen-w" if the terminal is wide (132 cols or more)). If even this entry cannot be found, “vt100” is used as a substitute.

Although `screen`'s mapping to different terminals is less than perfect, it is possible to improve the mapping by providing customized "screen.<term>" entries. The ncurses terminal database has done that since early 2001.

As along as the local and remote terminal databases are complete and up-to-date, things go well. When they are not, users encounter problems such as in

> Debian #854414 — screen: after sshing, some commands give error "Error opening terminal: screen.xterm-256color."

The discussion is rather long, with as they say, something for everyone. The resolution (adding documentation) does not really solve the problem, since the `screen` manual page has been available for some time.

Just to keep things interesting, ncurses 6.1 provides a new way to solve the problem. The `infocmp` program can print a terminal description in a a single line, which when assigned to the `TERMINFO` variable lets the library read the terminal description directly from the variable. Old-time developers who are knowledgeable about termcap might see a similarity, but that changes with a closer look:

- the terminfo information can be written to a single line (eliminating one of the problems with shell variable assignments), and
- the terminfo description is encoded either in base-64 or hexadecimal (allowing the binary data to be assigned safely).

This works with ncurses 6.1:

>     TERMINFO=$(infocmp -0qQ1) ssh remote

and if the `TERMINFO` variable has been added to the list of environment variables in the `ssh` and `sshd`, then ncurses 6.1 applications on the remote system will read the terminfo description from the environment variables. Applying the changed `TERMINFO` to the single `ssh` process is preferable to blindly setting it in your shell's initialization scripts.

That would not work with systems that do not use ncurses 6.1, but unless the `TERMINFO` variable is accepted in their respective `sshd` configurations, they will not be confused by this extension.

For those curious about other libraries, slang will ignore the “broken” `$TERMINFO` and rely upon its compiled-in terminfo list. Other problems can of course occur.

#### Problems with Cross-Compiling

I have done occasional cross-compiles of ncurses since 2003, using DJGPP as a target, and recently (writing this in 2010) some MinGW builds. For example

> TARGET=mingw32
> configure \
> --with-build-cc=gcc \
> --host=$TARGET \
> --target=$TARGET
> make

Cross-compiles of ncurses require compiling utilities which are then executed at build time. The utilities are wrappers around ncurses library functions, which means that some special #define's may be needed to compile them. In particular (until May 2010) cross-compiling the wide-character library required adding something like this:

> --with-build-cppflags=-D_XOPEN_SOURCE

Ncurses 5.7 introduced a separate problem. The terminal database distributed with it uses a feature that causes older versions of tic to hang. If you are cross-compiling, the database is installed using your system's copy of tic. You can work around the problem by either updating ncurses (5.7 was released in 2008), or substituting an older version of `misc/terminfo.src` in the build tree.

### Configuring NCURSES

#### Do I need all of those programs and libraries?

Well, I use them...

Wrong answer.
You may need only the ncurses library, or even just the terminfo database. The top-level Makefile in the build tree is designed to let you install various combinations according to your requirements. But there are a few constraints:

- You can install only the terminfo database by typing "make install.data". But you must have a copy of `tic` built. If you chose to build with shared libraries, you should first install the libraries and programs, e.g., with "make install.libs install.progs". Otherwise the shared libraries will not be found properly for the terminfo compiler to run.

- The version numbers attached to the shared libraries do mean something. Do not rename them (or link other versions to them).
  Version 5 is not compatible with version 4.
  Version 4 is not compatible with version 3.
  We have made corrections at each release to match the X/Open Curses interface specification. I have seen as many people complaining about mysterious problems with ncurses as I have seen people advising others to save time/space by linking them.

#### Do I need the C++ binding?

You may not need the C++ binding for ncurses. However, you should configure ncurses with C++ if it is available on your system. Otherwise, you will not be able to compile ncurses applications with the C++ compiler.

This point is not clear in the INSTALLATION instructions, having been thought too obvious to dwell upon. However, some distributors have “customized” ncurses, omitting the C++ binding to save space (or the time to issue separate "make install" commands for the components which they really need).

The problem is this:

- Both ncurses and C++ declare the bool type. It is part of each of their respective standards.

- There is no standard that says what the size of bool is.

- The ncurses interface uses bool.

The ncurses configure script determines the actual size used for bool by the C++ compiler on your system. If you suppress this configuration check, the default size for bool is not guaranteed to work with your compiler.

With 5.0, the configure script provides two options (`--without-cxx` and `--without-cxx-binding`). Use the former to suppress the configure checks for the C++ compiler, e.g., when there is no working C++ compiler on your system. Use the latter to omit the C++ binding, if you must.

#### Why does make menuconfig fail?

I can only guess (people having trouble in this area generally do not answer email ;-)

The Linux “make menuconfig” attempts to build a customized dialog program called `lxdialog`. This uses ncurses, which of course is why you are reading this question/answer.

- The development libraries or header files for ncurses may not be installed.

- The libraries may be installed in an unusual place. But in any case, /usr/src/linux/scripts/Makefile is simple to read, to see where `make` looks.

- You may have attempted to upgrade your C library, and did not complete the job by upgrading libraries that depend upon it.

#### Problem building with gcc 2.96.x

The C preprocessor in gcc 2.96 is broken. In particular, the C preprocessor has multiple bugs including

- does not handle whitespace correctly (breaks ncurses).

- cannot compile its own preprocessor output (breaks lynx).

These were apparently fixed in gcc 3.0.4 (do not waste time with gcc 3.0).

#### Problem building C++ interface with gcc 3.x

Since releasing ncurses 5.2, this has been the most frequent reason for referring people to the rollup patch. The problem is that the C++ bindings to C functions such as `vsscanf()` were altered (more than once, apparently as an afterthought) in preparing the gcc releases. Since the gcc changelog does not cite these changes except obliquely, and they are undocumented, it is possible that they may change again.

#### Testing for Memory Leaks

Perhaps you used a tool such as `dmalloc` or `valgrind` to check for memory leaks. It will normally report a lot of memory still in use. That is normal.

The ncurses configure script has an option, `--disable-leaks`, which you can use to continue the analysis. It tells ncurses to free memory if possible. However, most of the in-use memory is “permanent” (normally not freed).

Any implementation of curses must not free the memory associated with a screen, since (even after calling `endwin()`), it must be available for use in the next call to `refresh()`. There are also chunks of memory held for performance reasons. That makes it hard to analyze curses applications for memory leaks. To work around this, build a debugging version of the ncurses library which frees those chunks which it can, and provides the `exit_curses()` function to free the remainder on exit. The ncurses utility and test programs use this feature, e.g., via the `ExitProgram()` macro.

### Customizing NCURSES

#### How do I set up a private terminfo database?

If you must maintain your own terminfo database, SVr4 curses and ncurses both use the $TERMINFO variable to override the standard location of the terminfo database. Ncurses also provides two related extensions: the $HOME/.terminfo directory and the $TERMINFO_DIRS search path.

Though ncurses tests $TERMINFO first, otherwise it reads from $HOME/.terminfo before the standard location, and writes to that location after failing in other places. This design is a compromise which is made more complicated if you have configured ncurses with the --enable-termcap and --enable-getcap-cache options. Unless you are prepared to deal with the hidden conflicts, you should simply remove the $HOME/.terminfo directory.

If you do not wish to use $HOME/.terminfo (and are not able to replace ncurses on your system), ncurses 4.2 and later work properly if you replace that directory with a file so it cannot write terminfo entries which would conflict with the standard location.

The toe program can show a side-by-side comparison of terminal databases, making it simple to see conflicting entries from your private terminal database.

As noted, ncurses also provides the $TERMINFO_DIRS extension. Unlike $HOME/.terminfo, this allows you to specify one or more locations for the terminal database. When reading a terminal description, ncurses chooses the first one found. Using this feature, you can tell ncurses to look in your own database(s) as well as one or more system-defined locations.

The usual reason for creating a private terminal database is to work around inability to change the system's terminal database. Setting $TERMINFO suffices for most users, and happens to work with other implementations than ncurses. However, for non-ncurses implementations, it limits the user's environment to just the terminal database indicated by the $TERMINFO variable.

As noted in "Which terminfo database do I need?", there are a few older systems whose compiled terminfo files differ slightly from the SVr4 layout used by ncurses. While ncurses can be compiled to match the system's format (I do this), it seems to be a less-used feature. Packagers prefer the simpler approach of letting ncurses use its database and leaving the system applications alone. There are then these cases for constructing private databases in an NFS-mounted home directory, shared across different operating system types:

- the system's terminfo format is SVr4-compatible.

  - Use the $TERMINFO variable, e.g., to have all applications (ncurses and otherwise) use the same terminal descriptions.

  - Use the $TERMINFO_DIRS variable to make ncurses applications see a distinct set of terminal descriptions from the system, e.g., for “xterm”.

- the system's terminfo format is not SVr4-compatible (AIX for instance).

  - if ncurses is compiled to match the system's terminfo format

    - as before, you can set either $TERMINFO or $TERMINFO_DIRS according to whether you want to use the same definitions for all applications (ncurses and system).

    - choose a different location for the database, e.g., $HOME/.terminfo-aix to avoid conflict with other platforms.

  - if ncurses is not compiled to match the system's terminfo format, then it is likely that ncurses and the system curses/terminfo libraries cannot read the other's compiled terminfo files.

    - You can set $TERMINFO_DIRS to tell ncurses to look at its own terminal database; the system libraries will not look there.

    - Do not set $TERMINFO, since this will cause both to look in the same place.

A good place to start when customizing a shell initialization script for your private terminal databases is of course `uname`, since it is provided on the systems which are relevant to this topic, and its output can tell which system type is used. Alternatively (if your environment happens to have an inconsistent mixture of ncurses packages), the hostname is another place to get useful parameters for the initialization script.

As a rule, these settings should be done in the shell's login script rather than the one which is run on each shell initialization.

#### My terminal is not recognized

Usually this happens because you have not installed the `terminfo` database, or it is not in the proper location. If you do not, and (if ncurses happens to be configured to provide termcap support using the "--enable-getcap-cache" configure option) the application is unable to locate the terminfo database, the ncurses library will attempt to recover by reading `/etc/termcap`, translating it into a private terminfo database, i.e., a directory:

> $HOME/.terminfo

This directory can be a nuisance, because the termcap file often does not contain complete or consistent terminal descriptions. Remove it and correct the problem (i.e., install the `terminfo` database). Better yet, do not enable the feature (it has been disabled by default since late 1996).

You (or the person who configured ncurses) may have installed terminfo in the wrong, or an obsolete location:

- On Linux-based systems, as well as BSD variants such as FreeBSD and NetBSD the preferred location for terminfo is `/usr/share/terminfo`, with a symbolic link from `/usr/lib/terminfo` for compatibility with older applications. Prior to 1.9.9g, the `configure` script defaulted to a /usr/local prefix rather than /usr, necessitating an explicit

  > configure --prefix=/usr

- On other systems, the prefix defaults to /usr/local. You may wish to change this. Some users install ncurses replacing other versions of curses altogether. I don't do this. If you do, read the INSTALL file.

- Some packagers have gone further, configuring ncurses for a given terminfo location (which is not the system default), and then treating ncurses's terminfo database as “optional”. You can always recover in this case by setting the `TERMINFO` environment variable to point to the real terminfo database.

- Finally, prior to 1.9.9g, the actual terminfo directory resided in `/usr/lib/terminfo`. It was moved to `/usr/share/terminfo` to conform to file-system standards. The installation script attempts to determine if you have a real directory at the old location, and will not delete that (because some applications, such as `mc` and `screen` install special terminal descriptions that you would not want to accidentally delete. The best solution in this case is to move the old directory to the new location and install the new terminfo data, merging into the old data.

#### Why use terminfo instead of extensible termcap?

Several reasons:

- there is no standard for termcap. That is a drawback to developing applications using termcap. Amusingly enough, many of the termcap capabilities in common use now are defined in terms of terminfo, much like the `inch` is defined in terms of a `centimeter`.

- termcap libraries are not as fast, and have a long history of susceptibility to buffer overflows. See the discussion of tctest for example.

- terminfo supports conditional expressions.

- ncurses terminfo is extensible anyway. It has been since 1999 (release 5.0). If you give the `-x` option to `tic`, it compiles additional information which may be in the terminal description, using the syntax to determine types. If `-x` is omitted, `tic` warns about the unrecognized information.

As an example of how this extensibility feature can be used, consider the case of OpenQM, whose developers copied more than 1000 lines of ncurses library code into their application to support some extended terminal capability features. Here are two patches showing how that can be improved by removing the nonstandard features:

- Make the syntax standard
- Remove the unnecessary code

### What implementations of terminfo are extended?

This could be a much longer answer, but the FAQ is long. A really short, but unsatisfying answer might be just “ncurses and libraries written to work with its database or to imitate it.” Here is a compromise:

- Unix System V (mid/late-1980s) provided terminfo using a predefined set of terminal capabilities, which used 16-bit integers.
- If you wanted to change any of that, you had to modify the curses library and programs. AT&T did that, adding new capabilities, in its series of releases culminating in SVr4. Some vendors did that as well.
- Some marketing people might call that “extended” but programmers would not.
- X/Open Curses (early-1990s) documented SVr4's terminfo (removing some details).
  Vendors probably continued to add capabilities.
- In 1999, ncurses 5.0 provided a way to add user-defined capabilities (i.e., no program changes were needed).
- The ncurses terminal database could be used by existing Unix applications.
- The user-defined capabilities would not be noticed by applications using other implementations of curses.

Of course, termcap, unlike terminfo, is interpreted and users could always just add capabilities as needed (although the absence of a standard termcap was a drawback). That initial implementation addressed most of the supposed advantage of termcap over terminfo, except:

- A number in termcap was not limited to 16-bits, while ncurses continued to use 16-bits for compatibility with other implementations.
- The ncurses implementation allowed a capability name to be only one type (boolean or number or string).

A decade later, a few implementations were based on ncurses' extended terminfo:

- unibilium provided applications with a different terminfo reader for ncurses' extended terminfo.
- NetBSD abandoned termcap in favor of terminfo, and developed their own terminfo library and programs. The NetBSD implementation includes the same limitations relative to termcap as ncurses' initial terminfo extensions.

But there were few applications which used the extended information aside from xterm and tmux.

So far, that addresses only ncurses' initial implementation. But ncurses is still under development.

Extended numbers (32-bits) were provided by ncurses 6.1 early in 2018:

- There were no credible extant uses of termcap with large numbers, anyway, but extended numbers in ncurses were useful for a few who wanted to experiment with direct colors.
- The required format change for extended numbers briefly broke unibilium (as well as slang, which does use terminfo).
- NetBSD was not affected by that improvement. However (writing this more than a year later, in April 2019) some newer terminal descriptions would not work with NetBSD curses, if its terminal database were up-to-date (it was last updated in February 2017). Writing in mid-2020, future releases of NetBSD may provide this feature.

While developing the extended numbers feature for ncurses 6.1, the other limitation (one type per capability name) arose in an end-user application:

- Knowledgeable terminal developers provide terminfo (or termcap) descriptions for their program.
  Other developers simply copy/paste something that looks close.
- In this case, someone read the manual page for tmux where it describes terminfo extensions which it supports. and did not understand that the corresponding terminal description has to fill in some string-values. The `Se` and `Ss` capabilities had no values. The change was accepted anyway, late in 2016.
- Keeping in mind that copy/paste mentality, changes to ncurses' terminal database are more closely scrutinized (but see update, which fixed other problems but not this one). In this case, the error was overlooked because there was no routine testcase for tmux's extensions.
- A capability without a value is a boolean value, even if tmux would like to use it as a string.
- By itself, that would only cause tmux to not find the capability. The problem was that some descriptions used the capability correctly, and the types differed between descriptions while `tic` compiled the database.
- For example, this one is built up from several other descriptions with the `use=` clause. When `tic` builds the result, it must merge those, accounting for differences in the lists of extended capabilities.
- The initial implementation did not handle that properly; `tic` chose the wrong extended capability in building the merged terminal description. Since even a small change affects many lines of text, the damage was overlooked at first. Subsequent fixes a year later overlooked the problem.
- The mismatched string value was a problem because it told ncurses to expect a parameter when it was used, while the application did not expect to provide that (see tmux #1264).
- Eventually it was reported early in 2018, and the terminfo description fixed.

Fixing the terminal description is easy. Improving the tool takes more time. Development toward ncurses 6.2 made these changes:

- adding checks for the conventional extended capabilities, to warn when a capability would use an unexpected number of parameters, and disallow that setting (20190317).
- improving the terminfo-merging to handle differing types for extended capability names (20190427).

Although the problem was fixed in ncurses, users continue to recommend using the corrupt terminfo file (for example, tmux #1593). The first of those changes to ncurses addresses that source of error.

### Making NCURSES Fast

#### Why does my program scroll slowly?

Besides padding (i.e., time delay) information, which may be slowing your application down on a terminal emulator, ncurses provides two versions of scrolling optimization. The newer/improved version was incompletely tested at the time of release of ncurses 4.2, so it was marked experimental in the configure script.

The newer scrolling (hashmap) algorithm does not work properly in older versions of ncurses. Starting with ncurses 4.2, however, we recommend enabling this logic when configuring, using the --enable-hashmap option. It is configured by default in ncurses 5.0

#### Why does VT100 refresh slowly?

Some terminal descriptions contain padding (i.e., time delay) information. Ncurses uses this information to slow down the rate at which characters are sent to the terminal.

However, the vt100 terminal description, which is one of the most widely used (or misused) contains padding information for a real DEC VT100. It is not suitable as a replacement for the xterm terminal description. (Xterm requires no padding).

If you must use the vt100 terminal description, you may consider setting the NCURSES_NO_PADDING environment variable which is implemented in current versions of ncurses (since late 1998). That directs ncurses to ignore nonmandatory time delays in the terminal description.

### Making Color Work

#### How do I get color with VT100?

Sorry. Real vt100's do not do color (ANSI or otherwise). Likewise, vt220, vt340 do not support ANSI colors. You may be running a terminal emulator which does and do not like this explanation.

You get "color with VT100" by running a terminal (or emulator) that supports colors, and by setting up the terminal description so that ncurses knows how to perform basic operations (setting the foreground and background colors). See My terminal doesn't recognize color.

Ncurses does not “know” that your terminal does support color. You must tell it. Some terminals (e.g., the higher models of DEC's VTxxx series) provide status information to a host on the capabilities supported by a terminal. Unix hosts do not interpret this information to set your $TERM environment variable. Instead, $TERM is set based on the connection which you make with your computer (e.g., a device listed in the /etc/gettydefs or /etc/gettytab files). You can override this by setting $TERM to a correct value or setting $TERMINFO to a private database.

Ncurses does not by itself know that vt100's do not do color. The standard reference for VT100 is its reference manual. There is a copy of that on vt100.net (look for EK-VT100-TM-003_Jul82). There are of course contrary sources of information about color-vt100's. The earliest one that I have seen is this (a copy of which has also been found here), which (besides the misinformation in its opening paragraph) has more than one point where it differs from vt100:

- Terminal Setup. The example given refers to modes, saying that few are implemented correctly. But the example itself is incorrect, because it omits the "?" character which tells that the sequence is a DEC private mode. For comparison, see DECAWM in xterm's control sequences document.

- Fonts

  - vt100 has one “font”. Bold is not a font, but one of the video attributes which include blink, reverse, underline.

  - The term “font” is inappropriate; “character set” is correct.

  - The control sequence cited for switching fonts omits the character which identifies the character set to use.

- Cursor Control

  - Force Cursor Position is the standard HVP (Horizontal and Vertical Position).

  - Save Cursor is from ANSI.SYS rather than VT100.

  - Restore Cursor is from ANSI.SYS rather than VT100.

- Erase Screen states that the cursor moves to home. This is a well-known difference between ANSI.SYS and VT100. With VT100, the cursor does not move. Incidentally, ISO 6429 (ECMA-48) does not mention either behavior.

- Define Key is not a VT100 feature. It is a feature of ANSI.SYS.

- Set Display Attributes.

  - Bright. The standard and VT100 documentation refer to “Bold”.

  - Dim is not a VT100 feature.

  - Hidden is a VT220 feature, not found in VT100.

There are several copies of this document (usually missing the copyright notice) available around the Internet.

After Andrey Chernov added vt100-color and others to the FreeBSD termcap file in 2002, I discussed this with him, pointing out that while there are terminal emulators which do this, the hardware did not. He resolved the issue by adding a comment:

>     # For color-enabled terminal emulators

(See revisions 1.117 and 1.119).

Even with that clarification, there are others who conflate “ANSI”, “VT100” and color, for example

- Andys Terminfo Package
- Debian #241717

Ncurses does not have terminal descriptions such as vt100-color because those are inevitably an oversimplification. For related discussion, see my comments on "xterm-color".

#### My terminal doesn't recognize color

Check the terminal description, to see if it is installed properly (e.g., in `/usr/share/terminfo`) by looking at the output of `infocmp`.

It should contain the following capabilities (shown with infocmp -L):

  > `orig_pair` or `orig_colors`
  > and `max_colors`
  > and `max_pairs`

as well as

  > `set_foreground` and `set_background`
  > or `set_a_foreground` and `set_a_background`
  > or `set_color_pair`

The `orig_pair` and `orig_colors` capabilities are not required in ncurses 5.0 (SVr4 curses works properly without them). For the rest:

- `max_colors` and `max_pairs` are numbers, which (at least) should be nonzero.

  Prior to ncurses 6.1, those were signed 16-bit values. With ncurses 6.1 (and using the recommended ABI 6), it is possible to use signed 32-bit values except in interfaces where the requirement for binary compatibility would prevent this.

  Several of the terminal descriptions were updated in ncurses 6.1 to take advantage of this, e.g., using larger values for `max_pairs`. Older toolsets may not accept the larger values. Solaris and NetBSD curses assign any out-of-range capability a zero value.

  Like ncurses 6.0, ncurses 6.1 can be compiled to support the older ABI 5. In that case, `tic` and `infocmp` check for overflow, and limit values to 16 bits. Because of these added checks, it is possible to have ncurses ABI 5 and 6 on the same machine. In contrast, older ncurses releases use only the low-order 16 bits of the value, which may have the same effect as Solaris and NetBSD (the low-order 16 bits of 0x10000 is zero).

- The other capabilities are strings, used for the escape sequences that tell the terminal what colors it should use.

The most common complaint is that "I can see colors using `ls`, but not with ncurses applications". This is due to not having installed the `terminfo` database. GNU `ls` (in contrast to FreeBSD `ls`) uses its own data (with hardcoded SGR numbers and ignoring the back color erase (bce) feature supported in terminfo/termcap), which is unrelated to other applications. To be fair, GNU ls does have an environment variable (`LS_COLORS`) which can be used to customize the numbers a little, but in practice very few users modify it.

Other libraries or applications may recognize other environment variables to supplant the terminal description (see for example the discussion of COLORTERM), or even assign special meaning to different values of the `$TERM` environment variable, but ncurses uses only the terminal description.

#### My terminal shows some uncolored spaces

Even if your terminal supports the back color erase (bce) feature, you may still have problems using it.

We can blame the standard (ISO-6429 aka ECMA-48 aka “ANSI”). It is too simplistic, being descriptive rather than prescriptive. What is that, you might ask? It means that the standards writers used existing simplified descriptions by developers for the features rather than decomposing the features into distinct parts—and then making precise descriptions of those for testing compatibility of various implementations. The standard does not go into enough detail to prescribe a particular behavior.

Back color erase covers many (usually) related features, because there are many control sequences which might affect color, depending on the implementation. Here is a list—for each item there is probably at least one terminal type which differs from ncurses' assumptions. The list shows terminfo names with the standard control name, if any, in parentheses:

`sgr0` (`SGR 0`)

  The standard notes that this is "implementation-defined", and "cancels the effect of any preceding occurrence of SGR".

  For practical purposes, ncurses has to assume that the cancellation applies to the normal video attributes such as bold, underline, reverse, but possibly not affecting color. Color came into the picture fairly late in the history of terminals, and there have been some (such as color_xterm) where `SGR 0` had no effect on color.

`ed` (`ED`).

  The erase-display feature is assumed to fill the cleared display (or part of the display) with the current background color.

  Examples of terminals which do not do this include dtterm and teraterm 2.3.

`el`, `el1` (`EL`)

  The erase-line feature is assumed to fill the cleared line (or part of line) with the current background color.

  There is no standard requiring that the behavior of `EL` and `ED` should affect color in the same way. It is a design choice; ncurses assumes this.

`ech` (`ECH`)

  Erasing a character (which does not move any text on the screen) is assumed to fill the erased cells with the background color.

  Rxvt does not do this, though its behavior matches most of the other assumptions.

  For xterm, `ECH` is a VT220 feature. VT220s (and for that matter, none of DEC's VTxxx series before the VT525) did not implement ANSI color (or any style of color which you would use with ncurses). Rxvt's behavior was based on its developer's interpretation of DEC's documentation. XTerm's behavior on the other hand was based on (generally) agreeing with the developer of the Linux console.

`ich`, `ich1` (`ICH`)

  Inserting an empty cell at the current position is assumed to fill the empty cell with the background color.

  Note that this control does not erase as one would infer from back color erase. But it creates an empty cell.

`dch`, `dch1` (`DCH`)

  Deleting the cell at the current position shifts the remainder of the line left, introducing an empty cell on the right end of the line.

  Note that this control does not erase as one would infer from back color erase. But it creates an empty cell.

`il`, `il1` (`IL`)

  Inserting an empty line at the current position is assumed to fill the new empty line with the background color.

  Note that this control does not erase as one would infer from back color erase. But it creates an empty row.

`dl`, `dl1` (`DL`)

  Deleting the line at the current position shifts the remainder of the screen up, introducing an empty row on the bottom of the screen.

  Note that this control does not erase as one would infer from back color erase. But it creates an empty row.

`ind`, `indn` (nonstandard)

  Scrolling the text up is assumed to fill the newly empty line (at the bottom of the display) with the current background color.

  Indexing, aka “scrolling” is not covered in the standard. The behavior is completely implementation-dependent. This is a commonly used feature of XTerm.

  There are subtle differences in behavior still possible, beyond filling and not filling. For instance, if the scrolling was in response to printing text which wrapped, that may or may not (depending on implementation) fill the newly empty line with the current background color.

  For instance, a change in this area the Linux 2.6.26 console driver in April 2008 was reverted 6 months later. That was a bug for Linux console, because it broke more than 16 years of predictable behavior (since 0.96b in June 1992). Likewise it would be a bug for XTerm (and I have rejected patches to “improve” its behavior in this detail). But other terminals could do this intentionally as I observed of the “VT340” emulator bundled with the OnNet TCP/IP product of FTP Software in the mid 1990s.

  The standard, by the way, takes it for granted that text will wrap and force the display to scroll. But it uses the terms “wrap” and “scroll” in only a few obscure comments, and doubtless left much leeway for implementation-dependent behavior.

  XTerm of course implements scrolling because it was based on DEC's VT100, which does this. While a real VT340 did not support ANSI colors, one model of DEC's last terminal (the VT525) did. Its documentation indicates that it was released September 30, 1994 (more than two years after Linux's “new color model” was available). The DEC documentation mentions a setting (`DECECM`):

  > The Erase color selection controls the background color used when text is erased or new text is scrolled on to the screen. Screen background causes newly erased areas or scrolled text to be written using color index zero, the screen background. This is VT and DECterm compatible. Text background causes erased areas or scrolled text to be written using the current text background color. This is PC console compatible and is the factory default.

  While Linux console (and XTerm) treat the insert/delete character/line operations as an erasure, according to more than one developer with firsthand experience, the omission by DEC in this summary was intentional: their terminals did not do this.

`ri`, `rin` (nonstandard)

  Scrolling the display down is assumed to fill the newly empty line (at the top of the display) with the background color.

  Again, there is no standard behavior. There are only design choices and assumptions.

`csr` (nonstandard)

  Setting scrolling margins is assumed to limit erasures (and filling with background color) to those margins.

  This is a commonly used feature of XTerm. Vertical scrolling margins are not the only feature of this sort. There are also horizontal margins (VT320) and origin mode (VT100) which can affect the ability to move the cursor—and erase text. But ncurses does little at present with those, since (aside from XTerm), most terminal emulators support those features poorly or not at all.

The ncurses library for the most part assumes that bce means the particular set of choices made for Linux console and xterm. Not all popular terminals match those choices. The standard is silent on “correct” behavior. There are two ways that ncurses may handle these differences:

1. provide a terminal description which omits the specific capability which differs from the assumption, or

2. in the library itself, be more pessimistic in optimizing the given capabilities.

The former is preferred, of course. The library should not be cluttered up with special cases.

#### My xterm program doesn't recognize color

Another specific problem lies with the terminfo description xterm. There are several xterm- and xterm-like terminfo entries in ncurses' terminfo database, corresponding to different terminal emulators. Only one is named “xterm”, and that corresponds to the standard one. A fresh install of ncurses provides a choice between the current and previous standard ones:

xterm-new
  that is based on XFree86 xterm (plus updates since 2006, of course). See xterm's change log for details.
xterm-old
  This is the same as `xterm-r6`, e.g., the X11R6 xterm. That program (X11R6 xterm) does not support ANSI text color.

For either flavor, your packager may have customized the definitions for backspace and delete to match the conventions of your system.

A fresh install of xterm on top of ncurses installs its terminfo entry as “xterm”.

#### Why doesn't ncurses use `$COLORTERM`?

`$COLORTERM` is an environment variable originally used by some applications developers who were constructing programs that run on `rxvt`, a terminal emulator, using the `slang` library:

- It tells the `slang` library to ignore the terminal description, using a set of built-in capability strings which produce ISO 6429 (aka “ANSI”) color on that emulator.

  The choice of capability strings may work for other emulators, but in general does not (e.g., terminals which lack the back color erase capability, such as Tera Term 2.3, CDE dtterm and nxterm, SecureCRT and warp).

- `slang`'s documentation does not give useful information on what values are accepted for the variable. The only way you will know how to use it is by reading the source code of the program (or using cut/paste from someone who did that).

Viewed as a fallback, `$COLORTERM` is perhaps acceptable (ncurses can be configured with built-in predefined terminal descriptions), but as a modifier to existing terminal descriptions it only leads to confusion, since most emulators that support color differ in minor details from the model which is supported by `slang`.

For example, dtterm nominally emulates a DEC vt220. Someone who knows this, but is also told that it supports color may (based on the usual misinformation available in newsgroups) try setting $TERM to “ansi”, “linux” or "xterm-color". (Use `infocmp` to see why this is uniformly bad advice). This figure illustrates what goes wrong when following that advice:

There is a `dtterm` terminfo entry which provides correct behavior.

#### Why not just use TERM set to "xterm-color"?

ncurses has a terminal description named `xterm-color`. Users assume that means it will work properly for “any” xterm. That is incorrect. It combines the simplest form of ANSI colors with the older X11R6 xterm. Originally, `xterm-color` corresponded to the color_xterm from the mid-1990s. That was superseded by XFree86 xterm in 1996. That is better than nothing, however using it in modern xterm (or anything accurately claiming to be compatible), these problems would occur:

- selections from colored backgrounds will add unnecessary spaces to the pasted text.

- the function keys do not necessarily match (F1-F4 for instance), and will be incomplete (for example keys modified with shift-, control-).

- scrolling will be noticeably slower.

- some visual features (flash, hidden cursor) are not available.

- it will not work properly in `luit`.

Some terminal emulators may set this value; however it is unlikely that any current emulators implement this particular set of limited features. It is more likely that a more capable description exists or (given suitable documentation) that one could be constructed.

For instance, it has been reported that Mac OS X's bundled terminal emulator uses this value. However, reliable reports of its actual capabilities say that there are differences, which are addressed in ncurses as the `nsterm` entry. In this case, infocmp shows

>     comparing xterm-color to nsterm.
>         comparing booleans.
>             hs: F:T.
>             km: T:F.
>             npc: F:T.
>             xon: F:T.
>         comparing numbers.
>             colors: 8, 16.
>             ncv: NULL, NULL.
>             pairs: 64, 256.
>             wsl: NULL, 50.
>         comparing strings.
>             acsc: '``aaffggiijjkkllmmnnooppqqrrssttuuvvwwxxyyzz{{||}}~~', '``aaffggjjkkllmmnnooppqqrrssttuuvvwwxxyyzz{{||}}~~'.
>             blink: NULL, '\E[5m'.
>             civis: NULL, '\E[?25l'.
>             clear: '\E[H\E[2J', '\E[H\E[J'.
>             cnorm: NULL, '\E[?25h'.
>             dsl: NULL, '\E]2;\007'.
>             el1: NULL, '\E[1K'.
>             enacs: '\E)0', '\E(B\E)0'.
>             flash: NULL, '\E[?5h$<200/>\E[?5l'.
>             fsl: NULL, '^G'.
>             hpa: NULL, '\E[%i%p1%dG'.
>             ich: NULL, '\E[%p1%d@'.
>             ich1: NULL, '\E[@'.
>             invis: NULL, '\E[8m'.
>             is2: '\E[m\E[?7h\E[4l\E>\E7\E[r\E[?1;3;4;6l\E8', NULL.
>             ka1: NULL, '\EOq'.
>             ka3: NULL, '\EOs'.
>             kb2: NULL, '\EOr'.
>             kbs: '^H', '\177'.
>             kc1: NULL, '\EOp'.
>             kc3: NULL, '\EOn'.
>             kend: NULL, '\E[F'.
>             kent: NULL, '\EOM'.
>             kf1: '\E[11~', '\EOP'.
>             kf18: '\E[32~', '\E[22~'.
>             kf2: '\E[12~', '\EOQ'.
>             kf3: '\E[13~', '\EOR'.
>             kf4: '\E[14~', '\EOS'.
>             kfnd: '\E[1~', NULL.
>             khome: NULL, '\E[H'.
>             kich1: '\E[2~', NULL.
>             kmous: '\E[M', NULL.
>             kslt: '\E[4~', NULL.
>             meml: '\El', NULL.
>             memu: '\Em', NULL.
>             op: '\E[m', '\E[0m'.
>             rmam: NULL, '\E[?7l'.
>             rs2: '\E[m\E[?7h\E[4l\E>\E7\E[r\E[?1;3;4;6l\E8', '\E>\E[?3l\E[?4l\E[?5l\E[?7h\E[?8h'.
>             setab: '\E[4%p1%dm', '\E[%?%p1%{8}%<%t%p1%'('%+%e%p1%{92}%+%;%dm'.
>             setaf: '\E[3%p1%dm', '\E[%?%p1%{8}%<%t%p1%{30}%+%e%p1%'R'%+%;%dm'.
>             setb: NULL, '%p1%{8}%/%{6}%*%{4}%+\E[%d%p1%{8}%m%Pa%?%ga%{1}%=%t4%e%ga%{3}%=%t6%e%ga%{4}%=%t1%e%ga%{6}%=%t3%e%ga%d%;m'.
>             setf: NULL, '%p1%{8}%/%{6}%*%{3}%+\E[%d%p1%{8}%m%Pa%?%ga%{1}%=%t4%e%ga%{3}%=%t6%e%ga%{4}%=%t1%e%ga%{6}%=%t3%e%ga%d%;m'.
>             sgr: NULL, '\E[0%?%p6%t;1%;%?%p2%t;4%;%?%p1%p3%|%t;7%;%?%p4%t;5%;%?%p7%t;8%;m%?%p9%t\016%e\017%;'.
>             sgr0: '\E[m', '\E[m\017'.
>             smam: NULL, '\E[?7h'.
>             tsl: NULL, '\E]2;'.
>             vpa: NULL, '\E[%i%p1%dd'.

Additionally, Mac OS X 10.7 is reported to use `xterm-256color` as a default `$TERM` value. This differs from `xterm-color` in several ways, in particular, the support for bce. It also differs from the recommended `nsterm-256color` (infocmp reports 111 differences).

#### Why not just use TERM set to “xterm”?

It is easy to find people recommending just setting `$TERM` to “xterm”, noting that several developers have used that as a default value for their terminal emulators. However, this is usually (except for xterm itself) a bad idea. The reason that those terminal emulators use “xterm” is not because they actually match the behavior, but

- it seems too much work to install the correct terminal definition on each machine (this was the reason given for rxvt's having done so for several years), or

- it seems inconvenient to the user to put up with the absence of a given terminal description when making remote connections (which pass `$TERM` to the remote system).

However, “xterm” refers to a specific terminal emulator. Some of its details are widely emulated, while others (such as the function key definitions) are not.

Ncurses has provided accurate descriptions for the different terminal emulators for many years. While each terminal may implement escape sequences which are not in the others (none implement as much as half of xterm), what is important for curses applications is what can be represented in the terminal description. Using infocmp, here is the amount of difference seen by ncurses for commonly used terminal emulators as of January 2012:

> Counting differences from xterm with infocmp
> Description | Count
> --- | ---
> ansi (for reference) | 137
> konsole | 58
> linux | 123
> mlterm | 59
> nsterm (Apple Terminal) | 117
> putty | 128
> rxvt | 124
> screen | 107
> screen.xterm-new | 11
> vte (e.g., gnome-terminal) | 55
> xterm-color | 112
> xterm-new (current standard) | 0
> xterm-old (old standard) | 115
> vt100 (for reference) | 154

Noting that infocmp lists 182 capabilities for xterm-new, entries with more than a small number of differences demonstrate lack of compability of xterm "me-too's" versus xterm itself.

That only covers the features which are in the terminal description, and does not address differences between terminal emulators. For example, in mid-2017, an update to the xterm terminal description added the ECMA-48 `REP` (repeat character) control. It was part of xterm since January 1997, but a terminal description using the feature was part of xterm only (not ncurses). After adding it to ncurses, it was observed that:

- rxvt is unaffected, since it does not use `TERM=xterm`.
- mlterm and OSX Terminal supported `REP`, using `TERM=xterm`.
- VTE, konsole, PuTTY, iTerm2 did not support this standard, longstanding feature, of xterm although they set `TERM` to `xterm` or `xterm-256color`.
- screen and tmux use a different `TERM` setting, and seemed to work (although tmux had some other issue with the test).

Here are screenshots showing the problem, on the left correct and on the right incorrect:

#### Why not make “xterm” equated to “xterm-256color”?

It breaks things, in more than one way. Seriously, no one should be asking this question, but see Why not just use TERM set to “xterm”?. Still (writing in mid-October 2012), I see that the answer is needed.

First, some background is needed:

- SVr4 curses supported color terminals, defining names for the 8 ANSI colors.

- SVr4 curses used color pairs to reflect limitations of some hardware terminals which could not render all possible combinations of color. The color pair value was a 6-bit field (defined by `A_COLOR`) in the `chtype` values, which allowed for all combinations of those 8 ANSI colors.

- PDCurses 2.0 (November 23, 1992) set aside 7 bits for `A_COLOR`, but used only 6-bits.

- ncurses began using an 8-bit field for color pairs starting (probably) early in 1993, providing for all combinations of 16-colors (e.g., for CGA displays).

- X/Open started standardizing and extending curses shortly after. The result is a hybrid, with most of SVr4 curses present, but adding a new data-type `cchar_t` to hold wide characters. Incidentally, they provided an alternate way to encode colors. None of the Unix vendors did anything in this area other than store the same 8 ANSI colors inside the `cchar_t`, but they did provide room for more.

- At that time (the mid-1990s), it was not apparent how this additional room might be useful, and in developing ncurses we simply stored the color in `cchar_t` in the attribute member. That allowed only 8 bits (16 colors), just as in the `chtype` data.

- The xterm 256-color feature started with Todd Larason's patch, which I added in mid-1999 in patch #111.

- For the record, ANSI X3.64 did not define 256 colors, nor even 16 colors.
  Those (256- and 16-colors) are extensions defined by xterm and aixterm, respectively.
  There is no such thing as “ANSI 256 colors.” File that away with “VT100 colors.”
  An extension is just what it sounds like: something compatible with, but not part of the standard.

- Though we (including Steve Wall's changes for 88-colors) continued to refine the feature for some time, it was not at first used much by applications. For instance, though I added the terminal description to ncurses, it was only partly supported by ncurses until I added the extended color features beginning in January, 2005.

- The ncurses extended color feature added a new structure member to `cchar_t` which allows for as many color pairs as one can store in an integer.

- The change to `cchar_t` makes the library no longer binary compatible with ncurses ABI 5. It is part of ncurses ABI 6

- Even with that change, there are several features in the application interface using 16-bit signed integers, limiting color pairs to 32767, but allowing 256 colors for practical purposes.

Here are screenshots showing the ncurses test-program with extended colors, using menu entry “C”, added in that time period. The first uses normal-weight text:

and the second uses bold font:

Other terminal emulators adapted the feature before any noticeable use by applications. After noticing these and verifying their behavior, I added corresponding entries to ncurses' terminfo.src file. Here are relevant changes:

> 88/256-color Terminal Descriptions
> Date | Change
> --- | ---
> 1999/11/27 | add xterm-88color, xterm-256color
> 2002-06-22 | add rxvt-16color, ibm+16color
> 2005-01-29 | update pairs for xterm-88color and xterm-256color to reflect the ncurses extended-color support
> 2005-02-26 | add aixterm-16color to demonstrate 16-color capability
> 2006-02-18 | add nsterm-16color entry
> 2006-04-22 | add xterm+256color building block, and add gnome-256color, putty-256color, rxvt-256color
> 2007-07-14 | add konsole-256color entry
> 2008-08-23 | add Eterm-256color, Eterm-88color, and rxvt-88color
> 2009-10-03 | add linux-16color; add ccc and initc capabilities to xterm-16color
> 2010-02-06 | add mrxvt-256color
> 2010-06-12 | add mlterm+256color entry
> 2012-03-31 | correct order of use-clauses in st-256color
> 2012-08-11 | add nsterm-256color, make this the default nsterm

Things started to change around 2005-2006 as you can see by looking at the dates in the table. Red Hat #175684 gives some clue, stating that the "next version of Emacs has support for 256 color terminals". Emacs on the console by the way uses termcap, not terminfo and certainly not (n)curses.

I chose to add new entries rather than change xterm (and others) because they are incompatible. There is more than one aspect to consider:

- some applications on the same machine will blindly attempt to use all of the colors without being ready to handle more than 8/16 colors. There was for example more than one bug-report with Fedora of this type. The symptom was that text would be invisible (black on black). The bug reports were eventually closed without correcting the problem.

- connections to/from remote machines with a different notion of xterm will behave inconsistently.

- termcap-style (or the rare terminfo-style) applications on a given machine are the only ones that can use the -256color or -88color flavors. But aliasing those to xterm will break ncurses applications.

- not all termcap applications will work properly, depending on what definitions they see for the `AF` and `AB` (or the `Sf` and `Sb`) capabilities. That is because an optimal capability for these (as provided from ncurses' terminal database) is a conditional expression—something like this:

  >             :AB=\E[%?%p1%{8}%<%t4%p1%d%e%p1%{16}%<%t10%p1%{8}%-%d%e48;5;%p1%d%;m:\
  >             :AF=\E[%?%p1%{8}%<%t3%p1%d%e%p1%{16}%<%t9%p1%{8}%-%d%e38;5;%p1%d%;m:\

  Some applications (such as vim) may allow (or even embed, hard-coded) the much simpler, but less efficient variant corresponding to

  >             :AB=\E[48;5;%dm:\
  >             :AF=\E[38;5;%dm:\

  but doing that on an application-by-application basis is pointless. If a termcap application uses the ncurses library to send the escape sequences (using tgoto, for example), it is also redundant, because ncurses will return a usable terminfo string, and interpret it correctly.

- there is already a widely-distributed terminal entry with the desired features. Since it has proven to be inconvenient to use the xterm-256color name everywhere, renaming it to xterm will simply shift the problem without providing a solution.

- making incompatible changes to a widely-used terminal description produces bug-reports. I have limited changes of that type in xterm to describing new features, not changing existing features. Even with that, there have been complaints for each change. Consider

  SGR 22
    rant by an end-user, twelve years after the change in question (viewer discretion advisory). David Dawes was the first to point out that this change introduced a problem with remote systems. After some discussion we decided to keep it.
  Function-key modifiers
    In xterm's patch #94 I added function-key modifiers. In patch #167 I modified the protocol to address a problem with Emacs (though making it configurable). In the meantime, KDE and GNOME had copied the earlier feature into their terminal emulators. Ten years later, neither had updated to the 2002 version of xterm's function-keys. There were several reports, the first that I noticed appeared in Red Hat's system. For example see #127773. Ubuntu #96676 is another example (still unresolved in 2012).
  Meta-mode
    Debian #444250. Essentially the problem here was that adding a flag to the description telling how to enable/disable xterm's meta mode exposed a differing interpretation of meta mode in bash which dates back to around 1990.

Although ncurses (starting with release 5.5 in 2005) can be configured to support 256 colors, it seems that no widespread distribution was using the extended colors feature (certainly not Red Hat or Debian). That (and the extended mouse feature) were the main features for the "ABI 6", which could easily coexist with the usual "ABI 5" ncurses.

Without widespread use of ABI 6, there was no reason to change the primary flavor of any of ncurses' terminfo entries to the -256color or -88color flavor.

In the Debian distribution there was an attempt in 2008 on the part of the ncurses package maintainer to provide a migration path to ABI 6. That effort died, and (writing in October 2012) did not have a clear successor.

Just because it is not viable does not prevent others from assuming it is. For example:

- Debian #230990 asks for the extended mouse support. It was opened in February 2004.

- Debian #405602 took 18 months to move the xterm-256color entry from the ncurses-term to the ncurses-base package in mid-2008.

- Debian #532537 asks for a change of xterm to xterm-256color. It was opened in June 2009. As justification, it stated that "all Debian systems have been supporting the 256-colour interface for as long as anyone can remember". The package changelog for xterm states that the feature was added in January 2006, which when compared with the Debian release cycle makes it very far from "all Debian systems".

- In mid-2012, I noticed that Fedora 18 would have xterm aliased to xterm-256color.
  Some notes are in Fedora's wiki Features/256 Color Terminals. However, the proponents of the change place too much emphasis on just changing it and pay less attention to the ensuing problems.

- Even in early 2015, postings such as How can I get more colors? [Curses] [Python] [Terminal] were common.
  As I noted (and because my correction was twice deleted, promoted it to this FAQ):

  >     Not exactly (curses will not do what was indicated).  See the ncurses faq: Why
  >     not make “xterm” equated to "xterm-256color"?.  The terminal database will
  >     return appropriate strings usable by low-level applications, but curses
  >     applications will not use them.

  Specifically, this part of the “answer” is untrue:

  > If you run your program using `env TERM=xterm-256color yourprogram`, curses will enable 256 colors, and it will work fine as long as your terminal actually supports it!

  Because (unlike this FAQ), StackExchange postings are ephemeral, here also are my followup comments:

  - In this context, "low-level" applications include any which do their own screen optimization without using the curses high-level interface.

  - Urwid has display modules for curses and “raw”. It uses hard-coded escape sequences in the latter to provide 256 colors. (If it had used the terminal database to obtain the escape sequences, I would call the “raw” interface a low-level application).

  - The reason why the curses high-level applications do not display 256 colors is because that requires an ABI change - making packagers reluctant to introduce it.

  - The mention of “Fabulous” is moot (the link was dead in early 2015 when this faq was created). It is unlikely that it can be mixed with ncurses calls; there has been no discussion on bug-ncurses mailing list.

Finally (August 2015), I provided ncurses6 (ncurses 6.0). Releasing a new version is a different matter from getting it accepted and in wide use. Since packagers have been providing it for some time, the compatibility issues are of less concern.

That is, compatbility of ncurses was solved long ago. Terminal emulators (and their developers) are a different matter. As in Why not just use TERM set to “xterm”?, setting an incorrect `TERM` only leads to problems.

As of 2025, not much has changed. A few developers provide usable terminal descriptions; others rely upon copy/paste. Results for the latter are poor, in particular for those choosing to hard-code `TERM` to xterm-256color. Here is an illustration, showing the amount of difference in various terminal descriptions compared to xterm-256color:

xterm-256color
xterm-256color 100% =====================================================
Hardware
vt100 22% ===========~~~~~~~~~--------------------------------++
vt220 37% ====================~~~~~---------------------------+++
vt420 35% ==================~~~~~~~--------------------------++
X terminals
konsole 67% ===================================~~~~~~~~--------
mlterm 84% ============================================~~~~----
rxvt 37% ====================~~~~~~~~~~~~~~~~~~--------------++
urxvt 48% =========================~~~~~~~~~~~~~~~~~~--------++++
vte 80% ==========================================~~~------
xterm 96% ==================================================~
OpenGL terminals
alacritty 92% ================================================~---
contour 73% ======================================~~~~~~~~-----+
foot 85% =============================================~~~----
ghostty 87% ==============================================~~----
kitty 83% ============================================~~-----
wezterm 85% =============================================~-----
Non-X terminals
domterm 84% ============================================~-------
iterm2 58% ==============================~~~------------------+
linux 35% ==================~~~~~~~~~~-----------------------++
mintty 93% =================================================---++
ms-terminal 91% ================================================~---
nsterm 49% =========================~~~~~~~-------------------+
pccon 35% ==================~~~~~~~~~------------------------+
putty 41% ======================~~~~~~~~~~~-------------------+++
teken 32% =================~~~~~~-----------------------------

#### Why only 16 (or 256) colors?

Before getting to the point, some background is needed.

Curses applications run in terminals (or terminal emulators). They set colors for the screen and parts of it by sending additional characters (escape sequences) to the screen.

The ANSI standard described 8 colors, did not in any sense allude to more colors. This is a palette-based set of colors; there is no standard for how those colors are composed.

A few terminals recognize the aixterm 16-color extension (not part of any standard), e.g., xterm patch #39. Again, there is no agreement between different terminals on the actual colors used. (While xterm is configurable, some of the others are not).

Starting with xterm patch #111, there is the “xterm-256color” terminal type. Using SGR 38 and 48 in an arguably nonstandard manner (at the time there was no free access to ISO 8613-6), it provides a predefined palette of 256 colors which can be modified through escape sequences. With the terminals which imitate this (none matches xterm's behavior exactly), there are two problems:

- the colors differ

- the interpretation of the escape sequences is generally incomplete, e.g., not recognizing the sequences for modifying the palette or not accepting only one color per escape sequence.

These deficiencies are well known, easily demonstrated.

Sometime after xterm patch #111, a freely accessible version of ISO 8613-6 (ITU T.416) was made available. Some (mostly secondhand) discussion of the ramifications of this is in KDE #107487.

A small minority of terminals support an additional interpretation of SGR 38 and 48 alluded to in ISO 8613-6 as direct colour. The term “direct colour” has been interpreted as “24-bit mapping of RGB” (it is an interpretation, since the ISO standard referenced is not specific). What the standard actually says is:

> The first parameter element indicates a choice between:

> > 0 implementation defined (only applicable for the character foreground colour)

> > 1 transparent.

> > 2 direct colour in RGB space.

> > 3 direct colour in CMY space.

> > 4 direct colour in CMYK space.

> > 5 indexed colour.

> ...

> If the first parameter element has the value 5, then there is a second parameter element specifying the index into the colour table given by the attribute “content colour table” applying to the object with which the content is associated.

> ...

> If the first parameter element has the value 2, the parameter elements 3, 4 and 5, are three integers for red, green, and blue colour components. Parameter 6 has no meaning.

There is no “24-bit” in the standard.

As is often the case with the ISO terminal standards, there is little or no prior art to use as a basis for standardization of these features. Accordingly, the existing implementations differ:

- ISO 8613-6 prescribes a different syntax than that used for xterm patch #111.

- ISO 8613-6 does not specify the “colour table” it only mentions it.

- xterm provided a color table, with additional control sequences for modifying it.

- Konsole used the xterm syntax for its 256-color (indexed color) and direct color features, as noted in a README file.

  The example script, by the way, demonstrates the former (256-color feature) and was copied/renamed from xterm's sources, as shown here. As of February 2021, there is still no corresponding script for direct colour in Konsole's source repository.

  The direct color feature was largely ignored for a few years. There were occasional comments, such as this mid-2012 thread on the vim-users discussion group.

- Some attempts were made by GNOME developers to apply similar changes to other terminals; no coherent description was found summarizing the success of that endeavor.

- After some reflection, I provided in xterm (with patch #282, September 2012) support for the direct color feature:

  > modify `SGR 38` and `SGR 48` to accept RGB index, matching the closest entry in xterm's palette.

  Both that and the earlier 256-color feature are usable with either the ISO 8613-6 (colon) syntax, or the xterm patch #111 (semicolon) syntax. While xterm will accept either syntax indefinitely, the terminal description may change depending on circumstances:

  - The xterm+256color building block is used for legacy applications
  - The xterm+256color2 building block is used for standard applications

- On beginning this item (January 2014), none of the other terminals which I tested accepted the ISO 8613-6 syntax (there were some unverified reports).

- There are other syntax issues. In the changes for xterm patch #282 (and the earlier KDE changes), no one noticed or commented on this additional sentence from ISO 8613-6:

  > If the first parameter element has the value 2, 3, or 4, the second parameter element specifies a colour space identifier referring to a colour space definition in the document profile.

  The ISO document offers no help in deciding what values that identifier might have or how it might be used, but omitting it may be a nuisance. Interestingly enough, some developers copied the feature from xterm while citing the ISO document as the source.

Konsole's README is not specific (mentioning only “3-byte RGB color space”), but the current source-code refers to truecolor which is different from direct color. See for example the discussion of Visual Types in the X11R5 library documentation (1991):

> - For DirectColor, a pixel value is decomposed into separate RGB subfields, and each subfield separately indexes the colormap for the corresponding value. The RGB values can be changed dynamically.
> - TrueColor is treated the same way as DirectColor except that the colormap has predefined, read-only RGB values. These RGB values are server-dependent but provide linear or near-linear ramps in each primary.

Using that escape sequence for TrueColor makes it a non-standard implementation. To be fair, KDE's 2006 changes to provide 256-colors (and incidentally direct color) did not hint at TrueColor. That came from other people. Konsole mentions “truecolor” only in one place, setting the environment variable `COLORTERM` from KDE #371919, copying John Davis' magic variable for overriding `TERM`, and triggering whatever special feature he has in mind for s-lang. With one value or another, it (and other magic variables to amend this) dates back to mid-1995 (rxvt-2.11). Here is the complete documentation in s-lang mentioning the variable as of February 2017:

>       Of course not all terminals are color terminals. If the S-Lang global
>       variable SLtt_Use_Ansi_Colors is non-zero, the terminal is assumed to
>       be a color terminal. The SLtt_get_terminfo will try to determine
>       whether or not the terminal supports colors and set this variable
>       accordingly. It does this by looking for the capability in the
>       terminfo/termcap database. Unfortunately many Unix databases lack this
>       information and so the SLtt_get_terminfo routine will check whether or
>       not the environment variable COLORTERM exists. If it exists, the
>       terminal will be assumed to support ANSI colors and
>       SLtt_Use_Ansi_Colors will be set to one.  Nevertheless, the
>       application should provide some other mechanism to set this variable,
>       e.g., via a command line parameter.

Beyond the issue of escape sequences, konsole and xterm use different library calls for implementing direct color. This makes no difference to an application which might use those escape sequences, but bears some comment:

- konsole uses Qt. In its source code (see KDE repository), it stores the color information in a QColor class. The documentation mentions

  > QColor is platform and device independent. The QColormap class maps the color to the hardware.

  Because konsole's source code does not refer explicitly to QColormap, it relies on default behavior of the class.
  The documentation for QColormap gives half a clue, in its comment about modes. Qt's documentation is vague in many respects (in sharp contrast to MSDN), leaving developers no recourse other than reading its source code.

  Here is a starting point: Qt 4.8 src/gui/painting.

- In the 4.8 branch, we find that the QColormap class for X11 was doing essentially what xterm does, i.e., color maps.

- The 5.0 source (still in development at the time the vim_use discussion took place—released 6 months later), supported 256 colors as seen in QColormap. Beginning in March 2014, the class initialization distinguishes between 24-bit and 8-bit color. The X11-relevant details have been moved away from this class.

- Distinguishing between 8-bit and 24-bit color is a useful simplification for X11, since it trades off between storing an 8-bit value in one of the columns for the R/G/B structure versus storing three 8-bit values.

  XTerm checks for this special case to allow exact color matches. Otherwise, it uses the closest color match.

- Because xterm allows the application to set the palette which is used for either style of color (256-color or direct), providing “lot of colors” would have been pointless.

- Konsole has no provision for modifying the palette, in either case.

The implication of the direct colour feature is “lots of colors”. On the surface, that may seem attractive. However, there are several considerations:

- who will use it?
- how will they use it?
- when will they use it?
- where will they use it?
- how many colors do they need?
- what are the performance tradeoffs?

To answer the question, bear in mind that this is an area of special interest to only a handful of developers. End-users read “16 million colors” and uncritically accept arguments that they can effectively use this. However, there are only (at most) a few thousand characters on a terminal's screen at a time. That number of colors exceeds by a couple of orders of magnitude the ability of anyone to discern the differences and rely on those distinctions to aid them in viewing text.

Moving past the first couple of points, the availability of direct color depends on how the application uses the information. As a terminfo description, that works for applications which use the terminal database directly. The principal ones which come to mind are text editors (emacs and vi-clones). Generally their developers have chosen to make their task more difficult by remaining with termcap (which cannot express the relevant escape sequences). So they incorporate some hard-coded behavior. For instance, in a change to emacs in February 2017, the developer

- used the ncurses user-defined capability feature to define single-parameter strings named `setf24` and `setb24` which transform the parameter into the three parameters needed for direct color, and
- because emacs uses termcap and normally cannot read those, the developer added a call to the terminfo function `tigetstr` (which probably only works with ncurses, since only the termcap interface is initialized) to get the information, and
- if successful, replaces the capability read from termcap for normal coloring, and
- passes the result to the emacs-specific tparam (which by the way accepts four parameters which could have been used for R/G/B as most developers would expect).

Working through these obstacles, it is possible to “use” termcap to provide “lots of colors” without affecting the ncurses library. Termcap applications do not use much of ncurses; nor do their developers contribute significantly to ncurses. The emacs workaround was unsuitable for ncurses because emacs interprets the data in its own way, and displays the result independently of ncurses.

Some mailing-list comments indicate that the existing capabilities are not well-understood by developers, e.g., this discussion in October 2013. Taking the discussion into account, consider the linux-c terminal description dating from 1996. That sets up a palette using a color index value mapped to R/G/B components. Other longstanding uses in ncurses include these:

> linux-c-nc, putty, xterm-16color, and xterm+256color

Some additional comments on mapping colors using `initc` and `initp` are found in this discussion.

Applications which use ncurses are a different matter. Unlike termcap applications, curses libraries (and analogous ones such as s-lang) use combinations of the terminal capabilities to allow their applications to work on a wide variety of terminals. There are a few limitations, due to the early implementation of terminfo:

- 4096 size-limit on compiled entries

- 16-bit limit for numbers (to keep them small), which are all signed values

- Because some terminal types did not provide a way to set foreground and background colors independently, the concept of color pairs was introduced.

Using the ncurses 5 ABI, you have available 16 colors, or 256 pairs of colors. Using the ncurses 6 ABI, you have 256 colors, or 32767 pairs (the limit for a signed 16-bit number). That limit is good enough for realistic applications, which could not have that many character cells on a screen simultaneously (unless of course, using 1-pixel fonts to pretend to draw graphics, e.g., AA-lib). Since ncurses is used to draw text, that is not a valid issue.

S-lang does not implement color-pairs (or padding, etc.), However (reading the source code), it also is limited by the terminal descriptions, using a maximum color index value 32767 (15-bits—signed short). No method for changing 15 into 24 was noted in this discussion. However, that led to a bug report with a patch which isn't fully “ABI compatible”. John Davis was able to work around the obvious problems in this patch by splitting up the extended color field to use some space in his library's data structure. Otherwise, users would have had to recompile their applications to use the library, since the patch altered these features of the interface:

>     #define SLTT_BOLD_MASK  0x01000000UL
>     #define SLTT_BLINK_MASK 0x02000000UL
>     #define SLTT_ULINE_MASK 0x04000000UL
>     #define SLTT_REV_MASK   0x08000000UL
>     #define SLTT_ALTC_MASK  0x10000000UL
>     #define SLTT_ITALIC_MASK  0x20000000UL

If you read the source code, you will see that he did not solve the problem of changing 15 into 24 (as of February 2017, it still used a signed 16-bit limit for the number of colors).

No matter how one uses the limits based on the terminal database, scaling is needed to map onto the actual device.

Bypassing the limits which can be derived from the terminal database (and veering off into the swamp of hard-coded behavior), the idle spectator might ask “why not add a special ad hoc interface to (somehow) just do it?” One of VTE's developers asked for that (see mailing list thread from January 2014).

The problem is that you cannot “just do it”—both ncurses and s-lang do optimization to address their legitimate users (those who are using the superior performance due to working with characters, especially via remote connections). They have longstanding APIs which expose some of the related information. Adding an ad hoc interface will either break compatibility, or require duplicating information. Either way, most of the existing users would be adversely affected.

Some hint of this is given in GNOME #704449. Given the source of the comment, the effect is understandably understated. The usual reason given for wanting this feature has been for making pretty color schemes for text editors (e.g., this and this).

More generally, the way to “solve” the problem would be to abandon compatibility with X/Open Curses, using `int` where `short` is now used, and provide a new (incompatible) terminal database format to store bigger numbers. Incidentally, this would break applications which use the existing terminal database format, such as s-lang.

This extended item was prompted by an advertisement early in 2014 posted to the ncurses mailing list. That was while I was working on versioned symbols, needed to gain packager's acceptance for ncurses6. A hypothetical future release aimed solely at providing “lots of colors” could do each of the items mentioned in the previous paragraph. But it had no place in the ncurses6 plan, which required only recompiles, no source-changes.

Beginning with a fallacious premise (using a source known to be erroneous), its authors (the two individuals mentioned in this thread) selected specific instances in an attempt to persuade the reader that a majority of terminals implement TrueColor (“16 million colors”), and has a discussion page devoted to expanding this:

- Several entries (such as FinalTerm) are bogus.

- Some others involve a stretch, e.g., suggesting that the existence of some patch for PuTTY is going to make it do 24-bit colors for you.

- All of the VTE-based terminals are listed as if they were independent. Presenting the information this way makes it (perhaps) more convincing. Certainly, if you get to vote as many times as you choose, you can win any dispute.

Much of the discussion on the page is in the same vein, e.g., talking about standards, while at the same time discarding the technical details of ITU T.416 and ECMA-48 which began this story.

Besides the discussion on that page, there are several related items such as KDE #371919, repeating some of the invented facts from that page, e.g.,

> Unfortunately the maintainer of ncurses and terminfo is not interested at all in adding this possibility to terminfo, see e.g. https://lists.gnu.org/archive/html/bug-ncurses/2016-08/msg00036.html.

After the release of ncurses 6.1, the page's authors made minor, but not substantiative changes. In contrast, the changes made for ncurses 6.1 to implement and integrate extended numbers (and colors) took about a year to develop (see this page for the full diffstat):

>     # 602 files changed, 54948 insertions(+), 35233 deletions(-)

Those people are not contributors to ncurses. While comments are useful (sometimes) none of it was written by them.

Without significant revision, there is nothing more to discuss.

#### Ncurses resets my colors to white/black

This is the way SVr4 curses works. From the XSI Curses specification

> The start_color() function also restores the colors on the terminal to terminal-specific initial values. The initial background color is assumed to be black for all terminals.

If your terminal description does not contain the `orig_pair` or `orig_colors` capability, you will be unable to reset colors to the pre-curses state. This happens, for example, with `aixterm`.

However, if your terminal does support resetting colors to a default state, ncurses will use this when exiting Curses mode. Terminal types that do this include the Linux console, `rxvt` and the XFree86 `xterm`.

Ncurses 4.1 provides an extension `use_default_colors()` which allows an application running on a terminal which supports resetting colors to mix the default foreground and background colors with the 8 defined curses colors.

#### Why are red/blue interchanged?

You may notice if you are porting an application from SVr4 curses to ncurses (or the other way), that some versions of ncurses have some pairs of colors interchanged with respect to SVr4 curses. This is a bug in ncurses (sorry). Someone made an error translating terminal descriptions, and confused the setaf/setab terminal capabilities with the setf/setb capabilities.

The 8 colors black, red, green, yellow, blue, magenta, cyan, white are coded in the ANSI (setaf/setab) convention with red=1, green=2 and blue=4, while the older (setf/setb) uses red=4, green=2 and blue=1. SVr4 curses accommodates either, interchanging colors in the setf/setb to match the setaf/setab style. Ncurses' terminfo database incorrectly renamed the setaf/setab capabilities to setf/setb, making it incompatible with the SVr4 curses library.

This was corrected in ncurses 4.1, but incorrect in all preceding versions.

### Other Display Problems

#### Line-drawing characters come out as x's and q's

The x's and q's correspond to a table (from terminfo/termcap) which tells ncurses how to map the “alternate” character set to the terminal's set of graphic characters. The reference for this table comes from the vt100. If the unmapped characters appear, then the terminal emulator does not recognize the escape sequence for switching between normal and alternate fonts that is given in the terminfo description.

There are several cases of note:

- Terminal emulators which use a different escape sequence or different range for mapping the resulting characters. For instance the so-called vt100-compatibles such as Linux console and Tera Term.

- Terminal emulators which are locale-sensitive. Again, Linux console is a problem area when running in UTF-8 mode, since its nominal vt100-compatibility is further lessened by ignoring the escape sequences dealing with fonts. The `screen` utility also has the same problem; whether to make the implementation simple or to copy the Linux console. It ignores vt100-style font switching when the locale is a UTF-8 flavor.

- If you happen to be using Solaris, it is often configured to prefer its terminal database to ncurses, even when ncurses is installed. However, its terminal description for xterm omits the `enacs` which is used to enable line-drawing. This does not work well with applications such as `screen` and `luit`.

For the first case, you simply have to find the correct terminfo description. Fixing the latter is harder, since the damage is done outside ncurses. (Though one can easily make things compatible enough that this particular issue would never appear, that style of solution is not deemed proper by some coders).

The normal ncurses libraries support 8-bit characters. The ncurses library can also be configured (`--enable-widec`) to support wide-characters (for instance Unicode and the UTF-8 encoding). The corresponding wide-character `ncursesw` libraries are source-compatible with the normal applications. That is, applications must be compiled and linked against the `ncursesw` library.

The ncurses 5.3 release provides UTF-8 support. The special cases of Linux console and `screen` were addressed in development patches completed at the end of 2002.

#### Line-drawing characters come out as Latin-1 characters

Those capital A's with dots on top. Yes, that is almost always a mismatch with the terminfo description.

There are some special cases such as Tera Term which are related to the font.

#### Line-drawing characters do not appear

There is no character at all where the line-drawing should appear, and other characters may be shifted around the screen. This may happen on the Linux console, but also on some other terminal emulators. The line-drawing characters do not appear because the terminal emulator is treating them as illegal characters.

ncurses starts by assuming that the terminfo is correct, and overrides it for some special cases which are known to misbehave. See the discussion of `NCURSES_NO_UTF8_ACS` in the ncurses manpage for details.

#### Why does my cursor blink in Emacs?

Depending on Emacs, or other programs, the answer differs. Most often this question is raised by people using the Linux console.

There are three capabilities defined in terminfo which affect the cursor:

> Terminfo Cursor Capabilities
> Full name | Terminfo | Termcap | Description
> --- | --- | --- | ---
> cursor_invisible | civis | vi | make cursor invisible
> cursor_normal | cnorm | ve | make cursor appear normal (undo civis/cvvis)
> cursor_visible | cvvis | vs | make cursor very visible

The three capabilities appear in the terminfo database 128, 178 and 103 times respectively. Some of those terminfo entries are building blocks. For the entries reported by toe, there are 670 which modify the cursor, out of 1629 entries. Some of these allow only between invisible/normal or normal/visible. There are 159 which allow all three possibilities, as well as 27 which allow only one choice.

The cursor blinks because the application (Emacs for instance) uses the `cvvis` capability. “Very visible” for a terminal cursor generally means that it blinks. Various tradeoffs are possible, depending on the terminal between underline, block, blinking.

Applications modify the cursor either via curs_set (in ncurses) or by sending the appropriate escape sequence to the terminal using termcap or terminfo calls. While `curs_set` refrains from substituting one escape sequence for another missing one, this is not true of termcap/terminfo applications. Frequently they replace a missing `cvvis` with an available `cnorm`. After a while, the programmers forget the difference, and surprise their users when someone upgrades a terminal description.

The Linux console tie-in happened with ncurses in 1999, by adding `cvvis` to the “linux” terminal description.

Outside of Emacs, the replacement of a missing `cvvis` with `cnorm` is the most common cause of surprise.

But Emacs is different. It intentionally uses the "very visible" blinking cursor by default. There is documentation here. The earliest available version of the code from 1991 uses `TS_visual_mode` in this way.

#### Why does (fill in the blank) happen when I use two threads?

If you have a program which uses curses in more than one thread, you will almost certainly see odd behavior. That is because curses relies upon static variables for both input and output. Using one thread for input and other(s) for output cannot solve the problem, nor can extra screen updates help. This FAQ is not a tutorial on threaded programming.

Starting with ncurses 5.7, this implementation of curses provides the ability to configure and compile the library to help solve the problem by:

- reducing the use of static variables (see curs_sp_funcs(3x)),

- adding mutexes around the low-level terminal I/O,

- changing global variables such as `LINES` to “getter” functions (see curs_opaque(3x), and

- adding functions which an application can use to avoid those which rely upon global (or static) variables (see curs_threads(3x).

Almost all programs can be recompiled to use the “ncursest” or “ncursestw” libraries. Just recompiling is not enough to make a program thread-safe. As usual, some (re)design effort is probably needed.

The test-programs provided with ncurses (ncurses-examples) include a few which demonstrate this alternate configuration of the library: ditto, rain, worm.

### Keyboard Problems

#### My cursor keys do not work

For instance, you may press the up-arrow and see “OA” or “[A”, rather than having your program recognize the up-arrow.

The terminal description may be incorrect, or the program may not be making proper use of it. ncurses (and other programs which use terminal descriptions) simply match the characters sent by the terminal against a list of strings defined in the terminal description.

vt100's can send different strings for cursor-keys (and keypad-keys) depending on how they are initialized. Terminal emulations which provide vt100 functionality behave the same way. There are two modes:

normal mode
  This corresponds to the power-up state of the terminal. Cursor keys send escape sequences (strings beginning with the ASCII escape character) that mimic cursor-movement control sequences. Those begin with `escape [`. An up-arrow is `escape [ A` (also expressed as `CSI A`.
application mode
  This is the programmed mode of the terminal. Cursor keys send escape sequences that can be easily distinguished from cursor-movement control sequences. Those begin with `escape O`. An up-arrow is `escape O A` (also expressed as `SS3 A`.

The terminal description describes only one mode. Usually that is the application mode.

The terminal description tells how to initialize the terminal, e.g., to make the cursor-keys send application mode escape sequences:

- Long ago, when there were many types of terminals in use, some would send nothing for special keys unless the terminal was initialized in this way.
- Other terminals could move the cursor in local mode (not sending anything to the host computer).
- Finally, there were some which would send cursor-movement sequences unless initialized.

To accommodate all types of terminals, the convention was that a program would initialize the cursor keys when it needed them, i.e., to use the programmed mode of the terminal. That works well for full-screen programs. Terminal descriptions (usually) describe the application mode for this reason.

This convention does not work well for command-line programs, which do not initialize the terminal. Keys which differ between normal and application modes are not available for programs which do not initialize the terminal.

For example, the `readline` library (which was originally hardcoded, and did not use termcap or terminfo), exploited the feature of vt100's that their cursor-keys transmit something in normal mode.

The `readline` library (which is used by `bash`) did this for several years before someone connected it to a termcap library. Around that point, someone made a terminal description for the Linux console which “solved” the problem of initializing the terminal for `bash` by not initializing it at all. Cursor keys always send normal-mode strings with this arrangement.

Granted, that works—provided that the terminal is initialized consistently. If your terminal happens to “solve” the problem in a different way, e.g., by starting in application mode, and if your environment sets `TERM` to “linux”, you may have problems with your cursor-keys.

#### Alt-keys do not work in bash

Depending on the application, users expect an “alt” key to do one of two things:

- send an escape character before special keys such as cursor-keys, or

- act as an extended shift, allowing you to enter codes for Latin-1 values from 160 to 255.

xterm supports both features, e.g., with the `eightBitInput` and related resources.

Bash users have an extra problem in xterm when using a recent terminal description (since xterm patch #216). For completeness, I noted in the terminal description how an application can set/reset “meta” mode. It turns out that bash turns on meta mode if it is available. It was not an optional feature in bash; bash's developers assumed that you would use it. That is an odd assumption, since the feature is rarely implemented. There were (counting xterm) only three terminal descriptions in ncurses' terminal database providing this (the low-level blocks for Ann Arbor, SCO, and XTerm).

Making it configurable was proposed in a bug report (opened 2009-09-30):

>     Date: Fri, 12 Feb 2010 09:04:48 +0000
>     From: bugzilla_noreply@novell.com
>     To: dickey@his.com
>     Subject: [Bug 541379] ncurses linked programs always dump control characters
>             for TERM=xterm

>     http://bugzilla.novell.com/show_bug.cgi?id=541379
>     http://bugzilla.novell.com/show_bug.cgi?id=541379#c24

>     Dr. Werner Fink <werner@novell.com> changed:

>                What    |Removed                     |Added
>     ----------------------------------------------------------------------------
>                  Status|NEW                         |RESOLVED
>              Resolution|                            |FIXED

>     --- Comment #24 from Dr. Werner Fink <werner@novell.com> 2010-02-12 09:04:42 UTC ---
>     (In reply to comment #22)

>     On SLESS11-SP1 yo'll find a version of the bash/readline which
>     enables the user to configure _rl_enable_meta:

>     --- lib/readline/bind.c
>     +++ lib/readline/bind.c 2009-09-30 11:25:38.087930034 +0200
>     @@ -1473,6 +1473,7 @@ static const struct {
>      #if defined (VISIBLE_STATS)
>        { "visible-stats",           &rl_visible_stats,              0 },
>      #endif /* VISIBLE_STATS */
>     +  { "meta-mode",               &_rl_enable_meta,               0 },
>        { (char *)NULL, (int *)NULL }
>      };

More than three years earlier, bash's maintainer had expressed reluctance to address the issue. However, bash 4.1 added an “enable-meta-key” feature, dated 9 October 2009. That makes it possible for users to disable it:

>         `enable-meta-key'
>               When set to `on', Readline will try to enable any meta
>               modifier key the terminal claims to support when it is
>               called.  On many terminals, the meta key is used to send
>               eight-bit characters.  The default is `on'.

#### My home/end keys do not work

This is usually due to an incorrect terminal description. When it is not, it is due to the terminal emulator itself.

Application developers tend to hardcode references in their programs to the “home” and “end” key, forgetting that the presence of any particular function key depends on the terminal.

Part of the problem with terminal descriptions is due to the way xterm's terminal descriptions are used in ncurses. Because xterm emulates a VT220, the terminal descriptions provided with it follows the DEC keyboard convention, which does not provide home/end keys. Rather, it provides find/select keys. See for example the discussion of function keys and keypad.

On the other hand, the descriptions in ncurses reflect the Sun and PC keyboards which many people use. They define home/end keys for xterm.

However, some packagers for ncurses have pasted xterm's terminfo descriptions into the ncurses distribution. The effect is to remove the home/end key definitions from ncurses.

The problem is easily fixed by ignoring the packager's improvements and reinstalling the ncurses terminfo database. This section tells where to get it.

#### How can I use shift- or control-modifiers?

The standard response is "curses doesn't do that".

There are workarounds. Some explanation is needed first.

Most implementations of curses work with terminals that use serial communication. Generally those were inexpensive. Adding keys to the keyboard was probably less expensive than adding logic to handle different types of modifiers (such as shift). Terminals that could send different types of modifiers used to be rare.

However, the IBM PC provided a widely available platform with a keyboard that could provide modifier information. On the other hand, there was no standard protocol for sending the information on a serial line.

Most of the activity in exploiting this platform consisted of ad hoc implementations for computer consoles, such as for SCO, OS/2, etc., which associated the control-, shift- and alt-key modifiers with function-key numbering. That is, rather than attempting to extract information on the modifiers from function key expressed as a character string, the various combinations are numbered (using function-key number, multiplied by a code corresponding to the modifiers) and associated with the numbered function keys in the termcap/terminfo description.

For example, the `scoansi` description encodes the modifiers by an arbitrary sequence from the possible final characters for an ANSI control, e.g.,

> normal
>   kf1=\E[M, kf10=\E[V, kf11=\E[W, kf12=\E[X, kf2=\E[N,
>   kf3=\E[O, kf4=\E[P, kf5=\E[Q, kf6=\E[R, kf7=\E[S, kf8=\E[T,
>   kf9=\E[U,
> F13-F24 are shifted F1-F12
>   kf13=\E[Y, kf15=\E[a, kf16=\E[b, kf17=\E[c, kf18=\E[d,
>   kf19=\E[e, kf20=\E[f, kf21=\E[g, kf22=\E[h, kf23=\E[i,
>   kf24=\E[j,
> F25-F36 are control F1-F12
>   kf25=\E[k, kf26=\E[l, kf27=\E[m, kf28=\E[n, kf29=\E[o,
>   kf30=\E[p, kf31=\E[q, kf32=\E[r, kf33=\E[s, kf34=\E[t,
>   kf35=\E[u, kf36=\E[v,
> F37-F48 are shift+control F1-F12
>   kf37=\E[w, kf38=\E[x, kf39=\E[y, kf40=\E[z, kf41=\E[@,
>   kf42=\E[[, kf43=\E[\\, kf44=\E[], kf45=\E[\^, kf46=\E[_,
>   kf47=\E[`, kf48=\E[{,

Some combinations are missing (kf14 for instance corresponds to a back-tab).

A different scheme is used by `rxvt` (which was influenced by xterm and different hardware portability tradeoffs):

> kf1=\E[11~, kf10=\E[21~, kf11=\E[23~, kf12=\E[24~,
> kf13=\E[25~, kf14=\E[26~, kf15=\E[28~, kf16=\E[29~,
> kf17=\E[31~, kf18=\E[32~, kf19=\E[33~, kf2=\E[12~,
> kf20=\E[34~, kf3=\E[13~, kf4=\E[14~, kf5=\E[15~,
> kf6=\E[17~, kf7=\E[18~, kf8=\E[19~, kf9=\E[20~,
> kf21=\E[23$, kf22=\E[24$,
> kf23=\E[11\^, kf24=\E[12\^, kf25=\E[13\^, kf26=\E[14\^,
> kf27=\E[15\^, kf28=\E[17\^, kf29=\E[18\^, kf30=\E[19\^,
> kf31=\E[20\^, kf32=\E[21\^, kf33=\E[23\^, kf34=\E[24\^,
> kf35=\E[25\^, kf36=\E[26\^, kf37=\E[28\^, kf38=\E[29\^,
> kf39=\E[31\^, kf40=\E[32\^, kf41=\E[33\^, kf42=\E[34\^,
> kf43=\E[23@, kf44=\E[24@,

The pattern is not so obvious here. The developer who assigned the numbering chose certain combinations from a table which was too large to map into the available 60 numbered keys. Here is the complete table, noting that `F1` is the X11 code which is not necessarily synonymous with `kf1`:

> Rxvt Function-Key Modifiers
> X11 Key | Normal | Shift | Control | Shift+Control
> --- | --- | --- | --- | ---
> F1 | ESC [ 11 ~ | ESC [ 23 ~ | ESC [ 11 ^ | ESC [ 23 ^
> F2 | ESC [ 12 ~ | ESC [ 24 ~ | ESC [ 12 ^ | ESC [ 24 ^
> F3 | ESC [ 13 ~ | ESC [ 25 ~ | ESC [ 13 ^ | ESC [ 25 ^
> F4 | ESC [ 14 ~ | ESC [ 26 ~ | ESC [ 14 ^ | ESC [ 26 ^
> F5 | ESC [ 15 ~ | ESC [ 28 ~ | ESC [ 15 ^ | ESC [ 28 ^
> F6 | ESC [ 17 ~ | ESC [ 29 ~ | ESC [ 17 ^ | ESC [ 29 ^
> F7 | ESC [ 18 ~ | ESC [ 31 ~ | ESC [ 18 ^ | ESC [ 31 ^
> F8 | ESC [ 19 ~ | ESC [ 32 ~ | ESC [ 19 ^ | ESC [ 32 ^
> F9 | ESC [ 20 ~ | ESC [ 33 ~ | ESC [ 20 ^ | ESC [ 33 ^
> F10 | ESC [ 21 ~ | ESC [ 34 ~ | ESC [ 21 ^ | ESC [ 34 ^
> F11 | ESC [ 23 ~ | ESC [ 23 $ | ESC [ 23 ^ | ESC [ 23 @
> F12 | ESC [ 24 ~ | ESC [ 24 $ | ESC [ 24 ^ | ESC [ 24 @
> F13 | ESC [ 25 ~ | ESC [ 25 $ | ESC [ 25 ^ | ESC [ 25 @
> F14 | ESC [ 26 ~ | ESC [ 26 $ | ESC [ 26 ^ | ESC [ 26 @
> F15 (Help) | ESC [ 28 ~ | ESC [ 28 $ | ESC [ 28 ^ | ESC [ 28 @
> F16 (Menu) | ESC [ 29 ~ | ESC [ 29 $ | ESC [ 29 ^ | ESC [ 29 @
> F17 | ESC [ 31 ~ | ESC [ 31 $ | ESC [ 31 ^ | ESC [ 31 @
> F18 | ESC [ 32 ~ | ESC [ 32 $ | ESC [ 32 ^ | ESC [ 32 @
> F19 | ESC [ 33 ~ | ESC [ 33 $ | ESC [ 33 ^ | ESC [ 33 @
> F20 | ESC [ 34 ~ | ESC [ 34 $ | ESC [ 34 ^ | ESC [ 34 @

That is, the final character is again used to encode the modifiers. There are several terminals which use different final-character encoding schemes, e.g., dg (Data General), interix, and those based on `ansi.sys` or `cons25`.

xterm uses a different scheme, encoding the modifiers as a parameter. There are many combinations available. Here is a short example:

> kf1=\EOP, kf13=\E[1;2P, kf25=\E[1;5P, kf37=\E[1;6P,
> kf49=\E[1;3P, kf61=\E[1;4P,

All of that focuses on function keys. There are other special keys on the IBM PC keyboard, e.g., the editing keypad and cursor keys.

Here, conventional terminfo/termcap provides just a little help, but providing names for some of the shifted keys. xterm defines some of these:

> kDC=\E[3;2~, kEND=\E[1;2F, kHOM=\E[1;2H, kIC=\E[2;2~,
> kLFT=\E[1;2D, kNXT=\E[6;2~, kPRV=\E[5;2~, kRIT=\E[1;2C,

But xterm can also work for control-, alt-, and meta-modifiers. None of those are defined in conventional terminfo/termcap.

ncurses allows you to define extended descriptions, i.e., to make up your own names. The xterm terminfo descriptions do just that: they define names for the modified cursor- and editing-keypad keys which are just the xterm modifier code appended to the name for the shifted key. For example, the delete-key (kdc) can be represented as shown below:

> Example of Xterm Extended Key (DC)
> Xterm Code | Modifier | Extended Name
> --- | --- | ---
> 1 (or missing) | Normal | kdc
> 2 | Shift | kDC
> 3 | Alt | kDC3
> 4 | Shift + Alt | kDC4
> 5 | Control | kDC5
> 6 | Shift + Control | kDC6
> 7 | Alt + Control | kDC7
> 8 | Shift + Alt + Control | kDC8

Other terminal descriptions can be (and in ncurses, have been) modified to use this naming scheme for extended keys:

- gnome-terminal and konsole (for more than ten years) used an older version of xterm's encoding (deprecated in 2002 because the parameter can be mistaken for a repeat count). Although the encoding is different (and these terminals omit some combinations), the functionality is similar.

- rxvt also provides distinct escape sequences for modified cursor- and editing-keys.

By adding these to the terminal description, curses applications will see the keycode rather than individual characters when processing keypad mode.

There are a few limitations though:

- the keycodes for the extended keys are generated at runtime, so the application must ask what their values are using key_defined.

- compiled terminfo descriptions, though larger than termcap's 1023 bytes, are still limited to 4096 bytes. Many applications (such as those built using `slang`) rely on this limit. Applications can work around this by defining keys at runtime, using define_key.

#### How can I see what my keyboard sends?

All of the trouble-shooting for keyboard problems relies on you being able to see what the keys send.
You can do this in more than one way:

- Some implementations of the `cat` program have a `-v` option which tells it to show non-printing characters in visible form.
  These include all BSD and Linux-based systems, as well as AIX, HPUX and Solaris.

  While all of the extent Unix systems appear to have this feature, POSIX does not document it.

  You would use it by typing

  >     cat -v

  It has a few limitations:

  - it does not stop special characters such as control-C
  - the output format cannot be inverted to obtain the original inputs.

- You can suppress the terminal driver's interpretation of the first byte in a given key by first pressing `control-V` (the lnext or literal-next character).

  In practice, this is “good enough” since most of the terminals you might want to use will only have a leading escape character in the special key strings.

That makes it possible to see what your keyboard sends. There is a corresponding problem seeing what programs actually send to your terminal.

- A few platforms have `vis`, which first appeared in 4.4BSD. There is a corresponding `unvis` which can put the string back together (unlike `cat -v`). You would use this by using `script` to capture all of the bytes sent to your terminal, e.g., in a file named `typescript`.

- But `vis` is not available everywhere (e.g., AIX and Solaris do not provide it, nor are you likely to find it with a Linux-based system).

  At the end of 1995, I wrote a similar program named `unmap` based on a description of `vis`, and likewise `map` (like `unvis`) for completeness.

### Using Hardware (Real) Terminals

#### Why does reset log me out?

This is a limitation of real hardware terminals: resetting them will break the communications to the host temporarily. Some terminal interfaces will tolerate this. Others (most) will interpret this as hanging up, and log you out.

The reset is specified in the terminal description, e.g.,

> rs1=\Ec,

That is the hardware reset escape sequence for vt100. Some terminals provide enough control over their features that a very complicated substitute could be concocted for the normal reset which does not perform a hardware reset. In practice, this is not easily done.

#### Why do I get trash on the screen?

This is a problem of real hardware terminals. Cheap terminals and cheap interfaces do not do sophisticated flow control (e.g., XON/XOFF). Instead, they rely on a host which does not send them characters too rapidly. Remote terminal servers may provide flow control; direct console or serial port connections often do not. (If you are asking this question, you probably have inexpensive hardware).

Terminfo descriptions designed for these inexpensive terminals have delay times specified in the control sequences which take extra time, such as clearing the screen. For example, the vt100 description tells the application to wait 50msec after clearing the screen:

> clear=\E[H\E[J$<50>,

Note: the `slang` library does not implement delay times, and is not suitable for applications which require direct connection to a hardware terminal. The author of that library states that no one uses hardware terminals any more, suggesting that I add this information to the FAQ.

### Interaction with Other Programs

#### Redirecting I/O to/from a Curses application

In principle, you should be able to pipe to/from a curses application. However, there are caveats:

- Some (very old) curses implementations did not allow redirection of the screen. Ncurses, like Solaris curses, consistently writes all output to the standard output. You can pipe the output to a file, or use `tee` to show the output while redirecting.

- Ncurses obtains the screen size by

  - starting with the size from the terminal description,
  - then trying to query the output file pointer (unless you have disabled it using the use_tioctl call), and
  - finally using the environment variables LINES and COLS (unless you have disabled it with the use_env call).

  If you are redirecting output, then a query based on the file pointer will always fail (because a pipe is not a tty), having no effect on the computed size.

- Similarly, you can redirect input to an ncurses application. However, I have observed that the use of `setvbuf` (for better output buffering) interferes with the use of stream I/O on Linux-based systems (and possibly other platforms). Invoking `setvbuf` may (depending on the implementation) cause buffered stream input to be discarded. Ncurses does not use buffered input, however you may have an application that mixes buffered input with a curses session.

#### What about readline?

The `readline` library appeals to a number of people, who would like to use it within an ncurses application.

At first glance—but only for that instant—it appears that the library is flexible enough to substitute a different display driver, e.g., to output via something other than `tput()` and `putc()`. Close reading of its `display.c` file shows this is ultimately futile. Quoting (Brian Fox's comment from the early 1990s, still present in readline 6.1 in 2010) from that file gives some insight:

> /* This is the stuff that is hard for me. I never seem to write good
> display routines in C. Let's see how I do this time. */

John Greco suggests a different approach here, which discards ncurses' input functions (such as `wgetch`), using `rl_callback_read_char` to fill the `rl_line_buffer` array. That can be printed using ncurses.

#### Problems with Output Buffering

Ncurses shares with SVr4 curses a limitation which is documented in the C standard. To attain good performance, they buffer output data, e.g., with the `setvbuf` function (or equivalent, depending on the platform). The performance gain is noticable.

However, if your application spawns a subprocess, it will inherit the output stream from ncurses—still buffered. On several platforms this results in odd behavior, since normally the standard output is line buffered, making the output flushed at the end of each line. To solve this problem, your application should disable `setvbuf` before invoking the subprocess and restore it when resuming. That is, it should, but often cannot—that is the problem. The standard says that `setvbuf` must be called only after opening a stream and before performing any reads or writes with that stream.

If your application calls `initscr`, it uses the standard output, which ncurses assumes has not been written to, to which ncurses then applies buffering. (Caveat: The standard writers neglected to provide a mechanism for determining if the stream is indeed buffered). Adding a call to `setvbuf` to disable buffering may work or not. In at least one implementation, the C library continues using the buffer after the buffer is disabled, even if an `fflush` is first given. That is, it will produce a core dump.

The fix? Use `newterm` to initialize ncurses and manage the input and output streams yourself. For instance, you may simply open `/dev/tty` for input and output, and leave the standard input and output alone.

### Mice and Windows

#### I can't cut/paste in xterm

This is a general FAQ relating to xterm. When an application sets xterm to any of its mouse tracking modes, it reserves the unshifted mouse button clicks for the application's use. Unless you have modified the treatment of the shifted mouse button events (e.g., with your window manager), you can always do cut/paste by pressing the shift key while clicking with the mouse.

Ncurses sets the mouse tracking mode as a result of your application's calls to `mousemask`, which is an extension.

#### Handling `SIGWINCH` (resize events)

It is possible to make an application resize when running in a windowing environment (e.g., in an `xterm`). This is not a feature of standard SVr4 curses, though some curses implementations (e.g., HP-UX) support this.

Within ncurses, there are two ways to accomplish this. One relies on side-effects of the library functions, and is moderately portable. The other is an extension to SVr4 curses.

- `endwin`/`refresh` when invoked will briefly exit curses and reinitialize the display, picking up the new screen size. Ncurses will reallocate the `WINDOW` data (e.g., curscr, stdscr) to reflect the new limits.

- `resizeterm` can be invoked directly to make ncurses resize its `WINDOW` data. I use it in my directory editor ded to achieve flicker-free resizing via a signal handler for `SIGWINCH`.

  The documentation for HP-UX curses implies that they use a similar approach; I have been unable to make it work.

Ncurses 5.0 can be configured to establish its own `SIGWINCH` hander. In this configuration, the `wgetch` function returns a special keycode `KEY_RESIZE` when a resizing event is detected. The signal handler also sets a flag which the library checks with `is_term_resized`, then calls `resizeterm` (Caveat: `malloc` and `free` are not guaranteed to be safe for use in a signal handler).

There is a known problem using bash's checkwinsize misfeature. See Novell #828877, as well as the thread starting here on bug-bash, and of course the manpage for use_env. Shells which set `LINES` and `COLUMNS` might have been a good idea in 1995, but not as a rule more recently than that.

The `SIGWINCH` signal was a feature of SunOS (since 1984) rather than AT&T SystemV. SunOS also provided an `ioctl` call which could be used to obtain the terminal window's current size. Both aspects (`SIGWINCH` signal and `winsize` structure) were later incorporated in 4.3BSD (early 1985). Other systems, e.g., Apollo provided similar capabilities, independently of SunOS. The ncurses `resizeterm` function is based on an earlier function `resizewin`, written in April 1988 using the Apollo calls, and later modified to work with `SIGWINCH`.

Though long supported on Unix-like platforms, `SIGWINCH` had not been standarized for more than 30 year. Finally these related standardization features appeared in in P1003.1 issue 8 (October 2022):

- 0001053: Add a “size” mode to stty(1) (submitted 2016-05-10 19:12, published).

- 0001151: Introduce new signal SIGWINCH and functions tcsetsize(), tcgetsize() to get/set terminal window size (submitted 2017-06-19 16:41, renamed and published)

- 0001185: Additional 3rd option for getting line size. (submitted 2018-02-02 04:13, published)

#### Linking with GPM (Linux console mouse library)

Ncurses works correctly with the Linux GPM (general purpose mouse) library. However, early on some distributors tampered with the library, making it not generally useful, by linking in a portion of the BSD curses library to satisfy references for `Gpm_Wgetch`. That prevented one from using ncurses' GPM support.

GPM provides limited support for xterm mouse control sequences. This is implemented in `GPM_Wgetch`, which makes some unreasonable assumptions about the curses library's internal behavior of `wgetch`. In particular, GPM interferes with the logic which combines characters into function-key codes. GPM also uses as part of its xterm control sequences a pair which save/restore the mouse mode (and are not actually handled by any of the other terminal emulators).

On writing this faq in 1999, there were no applications that used this misfeature. Later (in 2005) there were still no curses applications which do, however w3m contains some contorted code to exploit this, by abusing the library interface: it defines several symbols that conflict with ncurses to intercept calls to `wgetch`, while using other symbols from ncurses as is. (There is also documented `Gpm_Getch`, but it is no longer present in the GPM source code).

Since version 1.10 GPM comes with a configure script, which allows the system builder to suppress this from the shared library, e.g.,

> configure --without-curses

You should verify that the shared library does not use the symbol `wgetch`. Version 1.16 lacked the configure script option to suppress this hook; removing libcurses.o from the list of objects in GPM's Makefile worked just as well. Version 1.17 built correctly when I tested it, however, though the changelog does not mention the change. It would seem that the issue would be long resolved. However, it is not.

Starting with ncurses 5.5, the recommendation is still the same: build the GPM library without the `Gpm_Wgetch` interface. ncurses 5.5 can dynamically load the GPM library on Linux, and that eliminates any reason to have the ncurses library built with an explicit dependency upon GPM.

Some of the GPM fixes are based on a quirk of the library: if `Gpm_Open` is called when the `TERM` environment variable contains “xterm”, it opens a connection which returns the raw character stream which might contain mouse escape sequences. It returns a special file descriptor (-2) which is easy to overlook in the normal checks on file descriptors which are valid only when positive. For quite a while as well, GPM and X could not co-exist. It was not uncommon to have some safeguards to turn off GPM when starting X. By around 2005, some fixes had been made to the X server to allow the two to run concurrently. That exposed some problems in ncurses which had not properly checked for the special file descriptors, and affected programs running in an xterm, e.g., dialog and ded which start/stop the mouse interface. For these, the GPM server would ultimately be locked up and not return from a call to `Gpm_Open`.

### Problems with Packages

#### Comments on packages

Packages are a good thing. Sometimes.

Not all distributions clearly distinguish between release versions of software, betas and alpha versions. (To be fair, not all producers distinguish these properly).

#### Ncurses 4/4.2/5.0

Ncurses 5.0 was not compatible with ncurses 4.2, however I frequently saw people advising others to “fix” programs that require the older library to make a symbolic link from the newer name to the older. That only works for simple applications, and not all of those.

Ncurses 4.0 and 4.2 were released respectively before and after X/Open finished their curses specification. Both were based on the draft specifications from 1995 and 1996. The released specification (available in 1997) differs in several places, mainly in the provisions for multi-byte character sets.

Late in 1998 through early 1999, I made corrections to the development version of ncurses to align it to the X/Open specification. Near the end of this, I realized that I had an opportunity to add an extension to ncurses which would make the terminfo format extensible, just as termcap is. It required a change to the `term.h` header. to allow the arrays for terminfo booleans, numbers and strings to be set at runtime. This had the effect of making programs not binary-compatible, but that was not a drawback, since it was already conceded that ncurses 5.0 would not be binary-compatible with ncurses 4.2 because of the X/Open changes. Only a few applications use `term.h`, and those would be fixed by a recompile.

One problem: Redhat packaged development versions of ncurses without distinguishing them from the release versions. We discussed the matter with them, but they did not wish to cooperate. Redhat 6.0 was released with almost all of the interface changes that comprised ncurses 5.0—as "ncurses 4.2". When ncurses 5.0 was released, they did not bother to read the release notes, and released that as "ncurses 4.2". Somewhat later, they added to the confusion by calling it "ncurses 4.0". Until mid-2001, much of this information was still available in Bugzilla.

Redhat continues to distribute development versions of ncurses without distinguishing between release- and development-versions.

#### rxvt's `$COLORFGBG` variable

Ncurses 5.2 added an experimental feature: support for rxvt's `$COLORFGBG` variable. This is a feature which tells the application what colors the default foreground and background correspond to. It is specific to rxvt: in general other terminal emulators assign colors for foreground and background which do not necessarily correspond to any of the ANSI colors. This feature was enabled in some rpm-based distributions, e.g., Mandrake and Redhat.

It worked for the configuration on which I tested, however there are two configurations. The format of the `$COLORFGBG` variable is not documented; you must read the C code to find how rxvt sets it. The two configurations correspond to whether the xpm library is used or not. If xpm is used, ncurses 5.2 sees the wrong value for the background, and display black-on-black.

Quick fix: unset `$COLORFGBG`.
Better fix: update the ncurses rpm (Mandrake did).

### Where is rxvt-unicode?

See the rxvt(-unicode) in ncurses page.

## How do I report bugs?

First, check to see if your problem is addressed in this FAQ. Read the INSTALL document, if you have not done so. However, it may not be a known problem. Read on.

- How should I report bugs?
- How do I report problems building ncurses?
- Updates to terminal database
- Why aren't my bugs being fixed?
- How are patches organized?

### How should I report bugs?

Contact the current maintainers at bug-ncurses@gnu.org.

To join the ncurses mailing list, please write email to `bug-ncurses-request@gnu.org` containing the line:

>     subscribe <name>@<host.domain>

This list is open to anyone interested in helping with the development and testing of this package.

There is an archive of the mailing list here:

> https://lists.gnu.org/archive/html/bug-ncurses (also https)

Otherwise, you may email directly to the maintainers, currently:

- Thomas E. Dickey <dickey@invisible-island.net>

If you send email only to one of the other authors, I will probably not see it. I prefer that bug reports go to the mailing list. (Occasionally I get private email cc'ing Zeyd and Eric, neither of whom has contributed since before 2000).

I get some of my bug reports via the ncurses mailing list, some via bug-tracking systems, and the others via direct email.

The mailing list is useful. When it began, more than half of the changes that were introduced without review in the ncurses mailing list introduced a bug. So I find it necessary to review proposed changes.

Refer to the standard reporting/patching procedures, for a start.

When sending patches, specify the version of ncurses that you are patching. All versions of ncurses have major, minor and patch-date numbers. Those may not be the same as a package revision number; it helps to identify that, so that I can relate it to the source.

There is a defunct "help-ncurses" mailing list, which I requested to be shut down long ago. I am not subscribed to that list.

### How do I report problems building ncurses?

This is a little different from reporting bugs. If you have a machine that I've not ported to, and have problems, I'll require the relevant information:

- `config.log`
- `config.status`
- `include/ncurses_cfg.h`
- log from running `configure`, with options
- log from running `make`, with options

A MIME attachment (preferably of the compressed files) is preferred, because logfiles can be awkward to send and receive via email. You may find the scripts which I use for building and saving logfiles useful.

If you're having trouble building on a known “good” platform, please make sure that you've got a current version of ncurses, and please read the installation instructions.

### Updates to terminal database

I attempt to verify users's proposed changes to the terminal database. Most of those are for terminal emulators, although there are still (2018) occasional updates for hardware terminals. Calling them all “applications”, there are some limitations which must be mentioned, based on developers' past abuse of common-sense guidelines:

- Updates for applications which are not generally available in a finished form are not suitable for inclusion.

  This is not the place for publishing in-development work which might change (or might not even be correct).

  Start by stating which packaged version of an application should be used for validating the updates.

- Terminal descriptions for applications which have some “string attached” (license fee, non-disclosure restriction, etc.), might be suitable for inclusion provided that there is no implication that they are the same as some less restrictively available application.

  For instance, there will be no aliases added in the less-restrictive application's terminal description mentioning the more-restrictive one.

Given those limitations, keep in mind that the terminal descriptions have to work with ncurses:

- Keep in mind that ncurses displays characters on terminals and get input (e.g., read characters) from the terminal. The predefined capabilities are used for one or both of those goals. Terminal descriptions may have user-defined capabilities, but if those capabilities are used to tell applications how to display on a terminal or get input from a terminal, they have be relevant to ncurses.

- ncurses is extensible. Developers have been able to define terminfo capabilities since the release of ncurses 5.0 in 1999.

  Other extended capabilities (i.e., not relevant to ncurses) can be added to the terminal database to support extensions used by other applications, but ncurses will not assign a name to those capabilities, nor will it define their behavior. Both aspects require documentation, and are the responsibility of the developer proposing the extension.

- Applications which infer characteristics of a terminal from the name of a terminal description are not relevant to ncurses. No changes will be made to the terminal database to accommodate those applications.

Furthermore:

- I use tic's consistency checks, tack and vttest, as well as custom scripts for testing basic functionality.

- When users provide custom scripts or programs which demonstrate a given feature, that helps a lot.

- If the source-code for the application is published, I will study that to amend the proposed changes. Often, developers propose changes based on cut/paste from other descriptions. Testing and review eliminate most of that problem.

- If a feature is present in the application but does not work as other implementations do, it will be removed or cancelled from the terminal description.

- Applications whose terminal descriptions which simply repeat another description might be considered for inclusion as aliases, but only if those have wide-spread recognizably different appearance.

### Why aren't my bugs being fixed?

Sorry. This is a hobby. There's a large backlog. Some changes pass review quickly, others are difficult, because one fix may break other functionality. My criteria are less stringent if you provide a short program that demonstrates the problem, or if you're modifying something that you maintain.

In any case, I will incorporate patches into my beta version only if I have reviewed the patch, tested it (if the patch is not obvious), and repaired any omissions (e.g., portability constraints). Occasionally I have patches (including my own) which cannot pass immediate review; these constitute most of my backlog. A small part of my backlog consists of issues which highlight incompatibilities between ncurses and SVr4 curses; these are listed in the TO-DO file.

I use the following guidelines:

- extensions (deviations from SVr4 curses) are allowed only if they do not modify the documented/observed behavior of the API.

- extensions are feature changes which cannot be implemented without modifying the library.

  For example, if you really need a function which interprets ANSI escape sequences, that can be done without modifying the library.

- I test behavior using unix curses (Solaris and others), and use the vendor's manual pages in conjunction with the X/Open Curses documentation.

- The Solaris XPG4 curses implementation is known to be badly broken; its SVr4 curses is usable for comparisons.

- The OpenSolaris source code (available via Illumos) is useful for gaining insight (and clarifying documentation), because it includes the Solaris SVr4 and XPG4 curses sources.
  However, Solaris' XPG4 curses differs from other vendors' implementations.

### How are patches organized?

Prior to version 4.0 I posted patches to the ncurses mailing list summarizing only my changes (after applying changes submitted by others). The intent was that people who followed the list closely could build developmental versions.

Generally (unless we find a serious error), I issue patches on Saturdays, since validating patches takes time.

Beginning with version 4.0, I maintain “complete” patches (my changes together with those that I have integrated). It is simpler, and does not require making complete snapshots as often.

- User-supplied patches that require no modification are always tagged with their name, making it simpler to follow the revision history.

- User-supplied patches that require some modification are still tagged, but my patch will have followup changes.

Most files have RCS identifiers. If you are maintaining ncurses in an RCS (or CVS, etc.) archive, you can keep in sync with this using the "-k" option of `ci`.

## Standardization

- POSIX Compliant?
- LSB Compliant?
- Y2K Compliant?

### POSIX Compliant?

That depends.

The library and utilities use (where possible) POSIX interfaces.

However, X/Open Curses is not part of POSIX (the 1003.x series, referred to as the Base Specifications). It is a different standard, updated less frequently, and bundled as part of the Single UNIX Specification.

Quoting from Advanced Programming in the UNIX Environment, third edition (Stevens and Rago):

> The third version of the Single UNIX Specification (SUSv3) was published by The Open Group in 2001. The Base Specifications of SUSv3 are the same as IEEE Standard 1003.1-2001 and are divided into four sections: Base Definitions, System Interfaces, Shell and Utilities and Rationale. SUSv3 also includes X/Open Curses Issue 4, Version 2, but this specification is not part of POSIX.1.

> ...

> In 2003, the Single UNIX Specification was updated, including corrections and new interfaces, removing obsolete interfaces, and marking other interfaces as being obsolescent in preparation for future removal. Additionally some previously optional interfaces were promoted to nonoptional status, including asynchronous I/O, barriers, clock selection, memory mapped files, memory protection, reader-writer locks, real-time signals, POSIX semaphores, spin locks, thread-safe functions, threads, timeouts, and timers. The resulting standard is known as Issue 7 of the Base Specifications, and is the same as POSIX-1.2008. The Open Group bundled this version with an updated X/Open Curses specification and released them as version 4 of the Single Unix Specification in 2010. We'll refer to this as SUSv4.

Additionally, ncurses

- provides extensions (features not addressed by X/Open Curses),
- is sometimes different from X/Open Curses, and
- provides extra libraries and programs (form, menu, panel as well as toe, tset)
  not documented by X/Open Curses.

The Austin Review mailing list archives frequently mention POSIX features which ncurses uses, but do not mention curses itself.

### LSB Compliant?

Perhaps the reverse. LSB largely complies with the ncurses and X/Open Curses documentation, but LSB is not used by ncurses.

The Linux Foundation's LSB (Linux Standard Base) combines POSIX and curses and other technical areas from other groups. ncurses is part of the LSB's Core Specification.

Currently in its 5th revision, the LSB describes some ncurses-specific features, e.g.,

- 15.7. Interface Definitions for libncurses lists a small number of functions which the LSB states is different from X/Open Curses Issue 7. However, it does not reference the ncurses manual pages (which go into far more detail about these differences).

- 15.9.1. ncursesw/curses.h gives an extract from the ncurses 5.9 header files, omitting most of the comments (and copyright notice).

- The LSB authors appear to be unaware that some of the definitions are not found in X/Open Curses, e.g.,

  >     #define KEY_MOUSE       0631
  >     #define KEY_RESIZE      0632
  >     #define KEY_EVENT       0633

- The summaries for libncurses and libncursesw include in the latter some common (ncurses-specific) functions such as those used in the mouse interface and window-resizing.

In some cases, the LSB is incorrect:

- LSB equates vw_scanw and vwscanw (the latter is obsolete, but LSB documents vwscanw rather than `vw_scanw`).

- In its errata for winstr, LSB references POSIX rather than X/Open Curses.

- LSB is too specific regarding the filenames for libraries. For ncurses, it documents `libncurses.so.5` and `libncursesw.so.5`.

  ncurses 6.0, released in 2015, provides the same interfaces, but uses 6 in the filenames.

  Occasionally, packagers trip over this (see RedHat #2076968).

- LSB appears to have no way of representing the same function being provided by more than one library. Its summary of the library interface for ncursesw does not document the fact that most of the functions are documented in X/Open Curses (see LSB bug reports #1761 and #3838).

- LSB does not account for the common ncurses configuration (since 1997) which splits the library into ncurses/tinfo (see LSB bug mailing list discussion in April 2016).

### Y2K Compliant?

Certainly.

The ncurses library does not store or retrieve dates in any form that depends on the year. Ncurses' use of time information is limited to

- computing the elapsed times, in fractions of a second,
- comparing file creation times, and
- sample programs that display the current time of day.

## Terminology

Ncurses is used primarily with terminal emulators. A few people use it with hardware terminals.

Terminals

  Short for data terminals, terminals provide users with the ability to enter and view data. The word terminal refers to something that is the endpoint.

  Terminals are generally not part of the computer, nor are they necessarily near the computer. Originally, terminals were connected to the computer by cables, later by local networks. The terminal emulator running in your computer's desktop environment is a special case—still using a network connection, but perhaps sharing keyboard and display with other terminal emulators.

Emulators

  An emulator of course is something which behaves like something else. In the case of terminals, these are programs which provide the same functionality as hardware terminals, or even other terminal emulator programs.

Control sequences

  Often referred to as escape sequences because many begin with the ASCII escape-character, control sequences are sequences of characters sent to a terminal to make it perform some operation. Most terminals (the ones that ncurses deals with) are asynchronous, and accept control sequences which update parts of the display. There are others, e.g., the synchronous "block-oriented" terminals such as the IBM 3278.

  The VT100's control sequences are used in many terminal emulators for example. In turn, most of those control sequences follow standards established by ANSI, ISO, ECMA. These are the most useful (and accessible):

  - ECMA-35 - Character Code Structure and Extension Techniques
  - ECMA-48 - Control Functions for Coded Character Sets

  The standards do not give exact functional definitions. For that, ncurses development relies on vendor documentation, analysis and comparison testing.

Consoles

  Originally console referred to the front panel of a computer, e.g., lights and switches, as well as the attached operator's terminal. The switches would do more than just turn the computer on and off.

  - Some machines provided special purpose switches which could enter data or control the computer's operation.

  - Later, the front panel was not so important for this purpose, and the operator's terminal was treated as the console. Many operating systems have a special terminal device for the system console terminal, e.g,.

    - `CON:` for MS-DOS
    - `/dev/console` on Unix-like systems.
    - `OPA0:` for VMS.

  - Still later, with video terminals becoming more common than printing terminals, the console terminal became an integral part of the computer. Several operating systems implement their console terminal as part of the kernel, e.g., Solaris, FreeBSD, Linux. Many people are confused by this, and refer to these as hardware consoles though they are not. They are programs. Generally they are not referred to as emulators simply because they usually are not made to imitate another terminal.

  - The console terminal now is used mainly when installing or reconfiguring the computer, rather than for routine control of its programs. Some system calls treat it specially, by using it as the destination for messages to the operator.

  The X Window system can be run on many of the console terminals. Sun's workstations for example did this. Few people used the console terminal on that hardware (which by the way was not VT100-compatible). Since X took over the computer's display, some way was needed to make the operator messages visible. The xconsole program did that; desktop systems provide analogous solutions. It is not necessary to use a terminal emulator to display operator messages. A few terminal emulators (such as xterm) can intercept console messages as an optional feature. The konsole program on the other hand, does not perform this function, notwithstanding its name. Rather, it is a terminal emulator.

  Microsoft Windows's treatment of console devices has changed:

  - In MS-DOS, there was one display device.

  - In Windows, there can be several console windows, each with its own console device. You can see the characteristics of the corresponding device by entering the command `mode con` into a console window. They are referred to as console windows because they provide partial compatibility with the MS-DOS console commands (including the device name `CON:`).

  - They are not terminal emulators however: these console windows do not by themselves respond to control sequences. MS-DOS provided a special device driver for this purpose called `ANSI.SYS`.

  - Windows provides an application programming interface (API) by which programs can treat the console window as a display.

  - Several terminal emulators have been written using the Windows console API which run in one of these console windows (for example, the Cygwin terminal before mintty).

  - There is also a port of ncurses using MinGW to these console windows. However, the ncurses MinGW port is a special case not using a terminal emulator. Like pdcurses, ncurses implements the Windows port using the Windows Console API. It does not rely upon `ANSI.SYS` or any of its successors.

  Like the Windows Console API, neither ncurses or pdcurses are terminal emulators. However, it is possible to write a terminal emulator using any of these application programming interfaces.

## Additional Reading

- For reference
- Dead trees
- Language bindings
- Other implementations
- Related applications
- Technically obsolete, but often cited
- Really old stuff
- Interesting but misleading

### For reference:

- The manpages, of course.

- X/Open Curses is not part of POSIX (the 1003.x series, referred to as the Base Specifications). It is a different standard, updated less frequently, and bundled as part of the Single UNIX Specification.

  Here are some useful links

  - 19 Apr 2013 – Issue 7 (pdf)

  - 15 Jul 1996 – Issue 4, Version 2

  - X/Open Curses, Issue 4, Version 2, Reference Pages

- These are based on ncurses:

  - NCURSES-Programming-HOWTO.
    An updated version is provided in the ncurses source-tree.

    The SGML and program examples are available as ncurses-howto-snapshots.
    A direct download is provided here.

  - Programmer's Guide to NCurses by Dan Gookin. Wiley, 2007.
    (my involvement is mentioned here).

    The source code for the examples is available on Koszek's page.

- These are useful reading as background material:

  - Solaris 11 Reference Manual Collection,
    manual pages section 3: Curses Library Functions

  - AIX General Programming Concepts: Writing and Debugging Programs,
    Chapter 2: The Curses Library

  - Unixware curses (a rare reference to “POSIX curses”).

  - IRIX64 curses

### Dead trees:

Intentionally ignoring the “door stops” which reprint manual pages, these books (long out of print) give useful information:

- UNIX Curses Explained. Berny Goodheart. Prentice Hall of Australia Pty Ltd. 1991. 287 pages. ISBN: 0-13-931957-5.

  Goodheart's book is useful for its historical perspective: he frequently mentions when a feature was added, and how it fit in.

- termcap & terminfo. John Strang, Linda Mui and Tim O'Reilly. O'Reilly & Associates, Inc., Sebastopol, CA, USA. Third edition with corrections, July 1992. 253 pages. ISBN: 0-937175-22-6.

  Originally published in 1985 to describe termcap and then updated to cover terminfo, this is useful, to a point: it omits any discussion of color, and the discussion of line-drawing is cursory (superficial).

  Strang also wrote Programming with Curses (1986), but that is not useful because it describes only 4.3BSD curses.

- Character User Interface Programming (UNIX SVR4.2). Edited by Claro Gomez. UNIX Press, Prentice-Hall, Inc. 1993. 720 pages. ISBN: 0-13-042581-8.

  The SVr4.2 book Programming with UNIX System Calls (1992) refers to this book for details on FMLI (not implemented by ncurses) and Extended Terminal Interface (ETI). ncurses provides libraries which correspond to the latter. The book is presented in tutorial manner, not a technical reference as such. It refers the reader to the manual pages for details. Interestingly, the system calls book's section mentioning Character User Interface Programming illustrates a technical blunder by implying that these two lines are the same length:

  >     ETI is a great package for creating forms and menus.
  >     ETI is the best package for creating forms and menus.

  About 40% of the book (chapters 6 through 13) covers the ETI consisting of the panel, menu, and form libraries as well as the soft-key support added to SVr4.2 curses. Only the last feature (soft-keys) was incorporated in X/Open Curses.

### Language bindings:

- Ada95 binding, from ncurses

- CHARVA (Java binding)

- Common Lisp binding

- Eiffel binding

- JavaScript binding

- OCaml binding

- Perl binding

- PHP binding

- Python binding

- Ruby binding

- Tcl/Tk Extensions & Information Page -> ncurses cTk

### Other implementations:

- PDCurses

- NetBSD

- OpenBSD

### Related applications:

- Xterminal's Home Page

- cdk Curses Development Kit (a library of widgets)

- dialog Script-driven curses widgets

### Technically obsolete, but often cited:

- 4.4BSD Documents -> original curses

- Escribir Programas con NCURSES

- Writing Programs with NCURSES

- A Hacker's Guide to Ncurses Internals

### Really old stuff

- As mentioned, the illumos sources are useful for comparison—up to a point. Those are based on the OpenSolaris release in 2005. It was not a complete Solaris source-release. For instance, some parts (such as FMLI) were not included.

  The copyright notices are helpful, but not definitive because they reflect only when someone recorded that a file was added to the AT&T sources, rather than when the program was written.

- For earlier implementations, the CSRG cdroms and Jonathan Gray's repository (converted from SCCS) are helpful. Both have problems: the 2BSD snapshots include files dated later than 3BSD, while the SCCS history goes back only to the end of 1979 (with six checkins), and checkins were not always done in a timely manner.

  The copyright dates in the source code are not helpful either, for a different reason. Early in 1985 (before the release of 4.3BSD (1986)), the developers added copyright notices for about half the source files, dating those to “1980” which is misleading. Many of those files were first published in 4.2BSD (1983), and did not exist in 1980.

### Interesting but misleading:

- Text-Terminal-HOWTO.
  I find the deliberate misstatements in this one to be fascinating. Still, there is some useful information as well.

- nanocurses (Haskell binding)
  It says (referring to the ncurses manpages):

  > Sections of the quoted documentation are from the OpenBSD man pages, which are distributed under a BSD license.

  First noticed in September 2008, this misattribution was still present as of July 2019, e.g., in the Debian libghc-hscurses-dev package (according to “git blame” the upstream comment was added in 2005).

  However, there is no “official” Haskell binding for ncurses. Other choices present other problems:

  - a terminfo package found here, which is undocumented. Reading the source hints that the developer does not understand how to develop thread-safe code.
  - another terminfo package found here also undocumented but (reading the source) it assumes ncurses with $HOME/.terminfo; but it does not handle ncurses 6.1 extended numbers (the last update to source-code was in 2015).

- Aside from a few grammatical and spelling fixes, OpenBSD developers have not contributed to ncurses documentation. That does not mean that the ncurses documentation in OpenBSD is identical. OpenBSD has made some questionable changes, e.g., the history and authors sections in the tset manual page (compare with ncurses).

- Even when the ncurses documentation is used without modification, it can still be misleading. For example, Interix (a “client system” or “environment” (like OS/2 EMX, U/Win, Cygwin, MSYS2) came with a port of ncurses.

  In the first announced version (e.g., 3.0), that appeared to be ncurses 1.9.9g based on the header files. However its documentation was a compressed help file “.chm” which used an earlier set of documentation from early 1996, e.g., ncurses 1.9.9e. The disparity was evident due to the way resizeterm and wresize were documented.

  The final version of Interix 3.5 (aka “SFU” or “SUA”) with updates to 2008 came with ncurses 4.2 (19980228) (apparently completed by Rodney Ruddock in September 1999). The documentation was not updated to match the software. Besides the resizeterm issue, the TechNet page Curses Applications on Interix for 3.0 mentions a problem which was fixed in June 1996:

  > function calls to getbkgd() needs to be replaced by wgetbkgd()

- But Interix is dead, last seen in Windows 7 Ultimate (January 14, 2020). This page is an example of a dead bug report. It was addressed in ncurses in 2017.

- A C# binding for curses, which supports some of ncurses and PDCurses extensions, first noted in mid-2009 here (apparently added anonymously by the program's author). Its page claimed that "Virtually every function in curses has its managed counterpart." I noted that it implemented less than half of the functions in ncurses 5.7 (206/414). As of early 2013, it is (like most SourceForge projects), apparently dead.

- The treatment of escape sequences here is a mish-mash of incorrect information from the DOS/Windows and Unix environments. There are several areas of confusion, e.g., mistaking common practice for standardization (and introducing confusion about the scope of the standards), as well as over-generalization. The worst offenders are of course anonymous.

  As an example of the problems in that source, in How can I remove the ANSI escape sequences from a string in python each of the answers to the question which cites that source has at least one error.

- The Python binding and tutorial bears some comment. On reflection, the comment is involved (see this page).

- The accepted answer for Colors in Man Pages has some issues:

  - It goes to some effort to state that termcap is better, and that `less` uses termcap, but explicitly uses the terminfo-based tput utility.
  - It introduces some capabilities which are not supported by the `less` pager, i.e., for superscripts and subscripts.

- The accepted answer for Fix terminal after displaying a binary file has some issues:

  - At the outset, a figure is shown which is actually irrelevant to the question. It shows the effect of sending a binary file to the terminal, but all of the odd characters are the Unicode replacement character. That is

    > used to replace an incoming character whose value is unknown or unrepresentable in Unicode

    One of the claimed advantages of UTF-8 is that it is stateless. In this situation, there is no action needed by the user to get the terminal to stop printing replacement characters, since the next output character is checked without regard to the previous character.

    If the terminal were not in UTF-8 mode, it would not print replacement characters, and users expect it to show line-drawing characters, e.g.,. as in How to fix a terminal after a binary file has been dumped inside it?, or (older) 4. Resetting your terminal in The Linux keyboard and console HOWTO. But bear in mind that the HOWTO (2002) is fairly recent: the `reset` program dates from around 1980, and has been an FAQ ever since.

  - After the interesting picture, two methods are suggested for fixing the terminal. For the first, the advice is to

    > 1. Hit Control + C a couple of times (Ctrl+C)
    > 2. Type the command reset and hit return

    That is partly helpful. No reason is given for using control/C, but suppose the binary file had sent a control to the computer asking it to do something (without providing a newline to complete the command). The `reset` command does two (types of) thing:

    1. it resets the terminal modes (in the computer's terminal driver)
    2. it resets the terminal itself (using escape sequences).

    Actually, the first part should not be needed, since the escape sequences possibly echoed by the binary file will not change the terminal modes. But typing `reset` is easy.

  - The other method says in effect to do each of the steps that `reset` would do, as separate commands. No explanation is given (nor would it help). The reason why one would use `stty sane` is to cleanup after a program which modified the terminal modes, e.g., from a text editor. That would be a different question.

    However, running `stty sane` may not restore your terminal to a state that you expect. It uses settings built into the `stty` program which may have no relation to the settings established when you logged in. For instance:

    - On some platforms (Solaris, Linux), it changes the `erase` character to ASCII DEL (127) — inconsistent with normal usage for the first, but consistent with the second.
    - But on HPUX, it changes `erase` to `#` (and it changes the `intr` character from control/C to ASCII DEL, and kills the `kill` character).
    - On Unix platforms, the same command also changes the parity handling, and turns off hardware tabs.

  - Despite all of that, there was some value to the answer: it prompted a review of the documentation for `reset` and `tput` (and improvements to the programs, so that “`tput reset`” would have the same effect as “`reset`”).

- Noticed in addressing some issues regarding the ncurses license, this site is (like another) apparently an anonymous work by an individual posing as a group of people for the sole purpose of disseminating misinformation.

- On a lighter note (partly), while looking for a suitable webpage for online manual pages, I noticed this page. Unlike another site, its formatting is reasonable, and is reasonably complete. However:

  - its ncurses-related manual pages are generated from a repository based on my development patches for ncurses, but
  - it does not process the sources to fill in configuration details (such as the actual name of the programs, the version information), and
  - it lacks most of the hyperlinks which are created by man2html (compare with my site), and
  - the boilerplate at the bottom probably should point to this ncurses page, rather than merely to the release announcement. I put a lot of information and links into the release announcements, but “home page” it is not. At the time of release for ncurses 6.1, according to FSF's Free Software Directory, my site was the homepage (dickey.his.com, which in turn forwards to invisible-island.net).

- Speaking of “home page”, Eric Raymond at one point had what he termed an "ncurses resource page". After the licensing issues were resolved, he modified his terminfo page to state that "there is no resource page for ncurses", and a few years later, again modified his terminfo page to point to the release announcement as the "ncurses home page".

## Copyright

Copyright © 1997–2025, 2026 by Thomas E. Dickey <dickey@invisible-island.net>
All Rights Reserved.

Permission to use, copy, modify, and distribute this software and its documentation for any purpose and without fee is hereby granted, provided that the above copyright notice appear in all copies and that both that copyright notice and this permission notice appear in supporting documentation, and that the name of the above listed copyright holder(s) not be used in advertising or publicity pertaining to distribution of the software without specific, written prior permission.

THE ABOVE LISTED COPYRIGHT HOLDER(S) DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL THE ABOVE LISTED COPYRIGHT HOLDER(S) BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.