Merge branch 'terminfo-dirs'

Closes #671
This commit is contained in:
Daniel Eklöf 2021-08-17 21:24:11 +02:00
commit f4da46350e
No known key found for this signature in database
GPG key ID: 5BBD4992C116573F
14 changed files with 191 additions and 81 deletions

View file

@ -48,6 +48,9 @@
### Changed ### Changed
* Terminfo files can now co-exist with the foot terminfo files from
ncurses. See `INSTALL.md` for more information
(https://codeberg.org/dnkl/foot/issues/671).
* `bold-text-in-bright=palette-based` now only brightens colors from palette * `bold-text-in-bright=palette-based` now only brightens colors from palette
* Raised grace period between closing the PTY and sending `SIGKILL` (when * Raised grace period between closing the PTY and sending `SIGKILL` (when
terminating the client application) from 4 to 60 seconds. terminating the client application) from 4 to 60 seconds.

View file

@ -17,6 +17,7 @@
1. [Use the generated PGO data](#use-the-generated-pgo-data) 1. [Use the generated PGO data](#use-the-generated-pgo-data)
1. [Profile Guided Optimization](#profile-guided-optimization) 1. [Profile Guided Optimization](#profile-guided-optimization)
1. [Debug build](#debug-build) 1. [Debug build](#debug-build)
1. [Terminfo](#terminfo)
1. [Running the new build](#running-the-new-build) 1. [Running the new build](#running-the-new-build)
@ -116,6 +117,35 @@ I also recommend taking a look at the bundled Arch
you intend to install a release build of foot, in which case you might you intend to install a release build of foot, in which case you might
be interested in the compiler flags used there. be interested in the compiler flags used there.
A note on terminfo; the terminfo database exposes terminal
capabilities to the applications running inside the terminal. As such,
it is important that the terminfo used reflects the actual
terminal. Using the `xterm-256color` terminfo will, in many cases,
work, but I still recommend using foots own terminfo. There are two
reasons for this:
* foots terminfo contains a couple of non-standard capabilities,
used by e.g. tmux.
* New capabilities added to the `xterm-256color` terminfo could
potentially break foot.
As of ncurses 2021-07-31, ncurses ships a version of foots
terminfo. I still recommend building and installing the version
shipped with foot, since:
* It will be more up to date (and more importantly, guaranteed to
match the installed version of foot).
* The ncurses version is missing several of the non-standard capabilities.
Foots terminfo will by default be built, and installed along with
foot itself. This can be disabled (for example, to simplify packaging
when the terminfo definitions are packaged in a separate
package). Instructions on how to do so is in [terminfo](#terminfo).
I recommend packaging foots terminfo files in a separate package, to
allow them to be installed on remote systems without having to install
foot itself.
### Setup ### Setup
@ -128,38 +158,64 @@ mkdir -p bld/release && cd bld/release
Available compile-time options: Available compile-time options:
| Option | Type | Default | Description | Extra dependencies | | Option | Type | Default | Description | Extra dependencies |
|-------------------------------|---------|-----------------------|---------------------------------------|--------------------| |--------------------------------------|---------|----------------------------|---------------------------------------|--------------------|
| `-Ddocs` | feature | `auto` | Builds and install documentation | scdoc | | `-Ddocs` | feature | `auto` | Builds and install documentation | scdoc |
| `-Dime` | bool | `true` | Enables IME support | None | | `-Dime` | bool | `true` | Enables IME support | None |
| `-Dgrapheme-clustering` | feature | `auto` | Enables grapheme clustering | libutf8proc | | `-Dgrapheme-clustering` | feature | `auto` | Enables grapheme clustering | libutf8proc |
| `-Dterminfo` | feature | `auto` | Build terminfo files | `tic` (ncurses) | | `-Dterminfo` | feature | `enabled` | Build and install terminfo files | tic (ncurses) |
| `-Dterminfo-install-location` | string | `${datadir}/terminfo` | Where to install the terminfo files | None | | `-Ddefault-terminfo` | string | `foot` | Default value of `TERM` | none |
| `-Dcustom-terminfo-install-location` | string | `${datadir}/foot/terminfo` | Value to append to `TERMINFO_DIRS` | None |
Documentation includes the man pages, the example `foot.ini`, readme, Documentation includes the man pages, the example `foot.ini`, readme,
changelog and license files. changelog and license files.
The two `terminfo` options are related, but control different aspects `-Ddefault-terminfo`: I strongly recommend leaving the default
of how the terminfo files are built, installed and used. value. This option is meant to be used as a last resort on platforms
where individual terminfo files cannot easily be installed.
`-Dterminfo` controls if the terminfo files should be generated _at `-Dcustom-terminfo-install-location` enables foots terminfo to
all_. If disabled, foots hardcoded default terminfo is co-exist with ncurses version. The idea is that you install foots
`xterm-256color` instead of `foot`. terminfo to a non-standard location, for example
`/usr/share/foot/terminfo`. Use `-Dcustom-terminfo-install-location`
to tell foot where the terminfo is. Foot will append this path to the
`TERMINFO_DIRS` environment variable in the client applications
process. The value is **relative to ${prefix}**.
`-Dterminfo-install-location` controls _where_ the terminfo files are Conforming applications _should_ look in `TERMINFO_DIRS` first, and
installed, relative to the installation prefix. The default is fallback to the builtin default (e.g. `/usr/share/terminfo`) if not
`${datadir}/terminfo`. found. Thus, it will prefer foots version, if it exists (which it
typically will on localhost), and fallback to ncurses version if not
(e.g. on remote systems, where foots terminfo package has not been
installed).
It also recognizes the special value `disabled`, that prevents the If set to `no`, foot will **not** set or modify `TERMINFO_DIRS` at
terminfo files from being _installed_. They are still _built_, and all. Use this if you do not intend to use/support foots terminfo
foots hardcoded default terminfo is still `foot`. It is intended to definitions at all.
be used when the terminfo files are packaged in a separate package
(something I **highly** recommend distros do).
To build the terminfo files manually, run `-Dterminfo` can be used to disable building the terminfo definitions
in the meson build. It does **not** change the default value of
`TERM`, and it does **not** disable `TERMINFO_DIRS`.
Example:
```sh ```sh
tic -x -o <output-directory> -e foot,foot-direct foot.info meson --prefix=/usr -Dcustom-terminfo-install-location=lib/foot/terminfo
```
The above tells foot its terminfo definitions will be installed to
`/usr/lib/foot/terminfo`. This is the value foot will append to the
`TERMINFO_DIRS` environment variable.
If `-Dterminfo` is enabled (the default), then the terminfo files will
be built as part of the regular build process, and installed to the
specified location.
Packagers may want to set `-Dterminfo=disabled`, and manually build
and install the terminfo files instead:
```sh
tic -o <output-directory> -x -e foot,foot-direct foot.info
``` ```
@ -347,6 +403,35 @@ ninja
ninja test ninja test
``` ```
### Terminfo
By default, building foot also builds the terminfo files. If packaging
the terminfo files in a separate package, it might be easier to simply
disable the terminfo files in the regular build, and compile the
terminfo files manually instead.
To build the terminfo files, run:
```sh
tic -o <output-directory> -x -e foot,foot-direct foot.info
```
Where _”output-directory”_ **must** match the value passed to
`-Dcustom-terminfo-install-location` in the foot build.
To compile and install directly (assuming the default
`-Dcustom-terminfo-install-location`):
```sh
sudo tic -o /usr/share/foot/terminfo ...
```
Or, if packaging:
```sh
tic -o ${DESTDIR}/usr/share/foot/terminfo ...
```
### Running the new build ### Running the new build
@ -355,17 +440,8 @@ You can now run it directly from the build directory:
./foot ./foot
``` ```
But note that it will default to `TERM=foot`, and that this terminfo Or, if you did not install the terminfo definitions:
has not been installed yet. However, most things should work with the
`xterm-256color` terminfo:
```sh ```sh
./foot --term xterm-256color ./foot --term xterm-256color
``` ```
But, I **recommend** you install the `foot` and `foot-direct` terminfo
files. You can either copy them manually (typically to
`/usr/share/terminfo/f` - but this depends on the distro), or
just install everything:
```sh
ninja install
```

View file

@ -98,7 +98,7 @@ package_foot-git() {
provides=('foot') provides=('foot')
DESTDIR="${pkgdir}/" ninja install DESTDIR="${pkgdir}/" ninja install
rm -rf "${pkgdir}/usr/share/terminfo" rm -rf "${pkgdir}/usr/share/foot/terminfo"
} }
package_foot-terminfo-git() { package_foot-terminfo-git() {
@ -107,6 +107,6 @@ package_foot-terminfo-git() {
conflicts=('foot-terminfo') conflicts=('foot-terminfo')
provides=('foot-terminfo') provides=('foot-terminfo')
install -dm 755 "${pkgdir}/usr/share/terminfo/f/" install -dm 755 "${pkgdir}/usr/share/foot/terminfo/f/"
cp f/* "${pkgdir}/usr/share/terminfo/f/" cp f/* "${pkgdir}/usr/share/foot/terminfo/f/"
} }

View file

@ -58,7 +58,7 @@ print_usage(const char *prog_name)
printf("Usage: %s [OPTIONS...] command [ARGS...]\n", prog_name); printf("Usage: %s [OPTIONS...] command [ARGS...]\n", prog_name);
printf("\n"); printf("\n");
printf("Options:\n"); printf("Options:\n");
printf(" -t,--term=TERM value to set the environment variable TERM to (foot)\n" printf(" -t,--term=TERM value to set the environment variable TERM to (%s)\n"
" -T,--title=TITLE initial window title (foot)\n" " -T,--title=TITLE initial window title (foot)\n"
" -a,--app-id=ID window application ID (foot)\n" " -a,--app-id=ID window application ID (foot)\n"
" -w,--window-size-pixels=WIDTHxHEIGHT initial width and height, in pixels\n" " -w,--window-size-pixels=WIDTHxHEIGHT initial width and height, in pixels\n"
@ -73,7 +73,8 @@ print_usage(const char *prog_name)
" -o,--override=[section.]key=value override configuration option\n" " -o,--override=[section.]key=value override configuration option\n"
" -d,--log-level={info|warning|error|none} log level (info)\n" " -d,--log-level={info|warning|error|none} log level (info)\n"
" -l,--log-colorize=[{never|always|auto}] enable/disable colorization of log output on stderr\n" " -l,--log-colorize=[{never|always|auto}] enable/disable colorization of log output on stderr\n"
" -v,--version show the version number and quit\n"); " -v,--version show the version number and quit\n",
FOOT_DEFAULT_TERM);
} }
static bool NOINLINE static bool NOINLINE

View file

@ -2832,7 +2832,7 @@ config_load(struct config *conf, const char *conf_path,
enum fcft_capabilities fcft_caps = fcft_capabilities(); enum fcft_capabilities fcft_caps = fcft_capabilities();
*conf = (struct config) { *conf = (struct config) {
.term = xstrdup(DEFAULT_TERM), .term = xstrdup(FOOT_DEFAULT_TERM),
.shell = get_shell(), .shell = get_shell(),
.title = xstrdup("foot"), .title = xstrdup("foot"),
.app_id = xstrdup("foot"), .app_id = xstrdup("foot"),

View file

@ -9,12 +9,6 @@
#include "user-notification.h" #include "user-notification.h"
#include "wayland.h" #include "wayland.h"
#ifdef HAVE_TERMINFO
#define DEFAULT_TERM "foot"
#else
#define DEFAULT_TERM "xterm-256color"
#endif
#define DEFINE_LIST(type) \ #define DEFINE_LIST(type) \
type##_list { \ type##_list { \
size_t count; \ size_t count; \

View file

@ -57,7 +57,7 @@ the foot command line
*-t*,*--term*=_TERM_ *-t*,*--term*=_TERM_
Value to set the environment variable *TERM* to (see *TERMINFO* Value to set the environment variable *TERM* to (see *TERMINFO*
and *ENVIRONMENT*). Default: _foot_. and *ENVIRONMENT*). Default: _@default_terminfo@_.
*-T*,*--title*=_TITLE_ *-T*,*--title*=_TITLE_
Initial window title. Default: _foot_. Initial window title. Default: _foot_.

View file

@ -29,8 +29,8 @@ in this order:
by prepending a '-' to argv[0]. Default: _no_. by prepending a '-' to argv[0]. Default: _no_.
*term* *term*
Value to set the environment variable *TERM* to. Default: _foot_ Value to set the environment variable *TERM* to. Default:
or _xterm-256color_ if built with _-Dterminfo=disabled_ _@default_terminfo@_
*font*, *font-bold*, *font-italic*, *font-bold-italic* *font*, *font-bold*, *font-italic*, *font-bold-italic*
Comma separated list of fonts to use, in fontconfig format. That Comma separated list of fonts to use, in fontconfig format. That

View file

@ -24,7 +24,7 @@ terminal has terminated.
*-t*,*--term*=_TERM_ *-t*,*--term*=_TERM_
Value to set the environment variable *TERM* to (see *TERMINFO* Value to set the environment variable *TERM* to (see *TERMINFO*
and *ENVIRONMENT*). Default: _foot_. and *ENVIRONMENT*). Default: _@default_terminfo@_.
*-T*,*--title*=_TITLE_ *-T*,*--title*=_TITLE_
Initial window title. Default: _foot_. Initial window title. Default: _foot_.

View file

@ -2,6 +2,12 @@ sh = find_program('sh', native: true)
scdoc_prog = find_program(scdoc.get_pkgconfig_variable('scdoc'), native: true) scdoc_prog = find_program(scdoc.get_pkgconfig_variable('scdoc'), native: true)
conf_data = configuration_data(
{
'default_terminfo': get_option('default-terminfo'),
}
)
foreach man_src : [{'name': 'foot', 'section' : 1}, foreach man_src : [{'name': 'foot', 'section' : 1},
{'name': 'foot.ini', 'section': 5}, {'name': 'foot.ini', 'section': 5},
{'name': 'footclient', 'section': 1}, {'name': 'footclient', 'section': 1},
@ -10,10 +16,16 @@ foreach man_src : [{'name': 'foot', 'section' : 1},
section = man_src['section'] section = man_src['section']
out = '@0@.@1@'.format(name, section) out = '@0@.@1@'.format(name, section)
preprocessed = configure_file(
input: '@0@.@1@.scd'.format(name, section),
output: '@0@.preprocessed'.format(out),
configuration: conf_data,
)
custom_target( custom_target(
out, out,
output: out, output: out,
input: '@0@.@1@.scd'.format(name, section), input: preprocessed,
command: [sh, '-c', '@0@ < @INPUT@'.format(scdoc_prog.path())], command: [sh, '-c', '@0@ < @INPUT@'.format(scdoc_prog.path())],
capture: true, capture: true,
install: true, install: true,

2
main.c
View file

@ -82,7 +82,7 @@ print_usage(const char *prog_name)
" -l,--log-colorize=[{never|always|auto}] enable/disable colorization of log output on stderr\n" " -l,--log-colorize=[{never|always|auto}] enable/disable colorization of log output on stderr\n"
" -s,--log-no-syslog disable syslog logging (only applicable in server mode)\n" " -s,--log-no-syslog disable syslog logging (only applicable in server mode)\n"
" -v,--version show the version number and quit\n", " -v,--version show the version number and quit\n",
prog_name, prog_name, DEFAULT_TERM); prog_name, prog_name, FOOT_DEFAULT_TERM);
} }
bool bool

View file

@ -17,10 +17,11 @@ if cc.has_function('memfd_create')
endif endif
add_project_arguments( add_project_arguments(
['-D_GNU_SOURCE=200809L'] + ['-D_GNU_SOURCE=200809L',
'-DFOOT_DEFAULT_TERM="@0@"'.format(get_option('default-terminfo'))] +
(is_debug_build (is_debug_build
? ['-D_DEBUG'] ? ['-D_DEBUG']
: [cc.get_supported_arguments('-fno-asynchronous-unwind-tables')]) + : [cc.get_supported_arguments('-fno-asynchronous-unwind-tables')]) +
(get_option('ime') (get_option('ime')
? ['-DFOOT_IME_ENABLED=1'] ? ['-DFOOT_IME_ENABLED=1']
: []) + : []) +
@ -34,6 +35,19 @@ add_project_arguments(
language: 'c', language: 'c',
) )
default_terminfo_install_location = join_paths(get_option('datadir'), 'foot', 'terminfo')
terminfo_install_location = get_option('custom-terminfo-install-location')
if terminfo_install_location == ''
terminfo_install_location = default_terminfo_install_location
endif
if terminfo_install_location != 'no'
add_project_arguments(
['-DFOOT_TERMINFO_PATH="@0@"'.format(
join_paths(get_option('prefix'), terminfo_install_location))],
language: 'c')
endif
# Compute the relative path used by compiler invocations. # Compute the relative path used by compiler invocations.
source_root = meson.current_source_dir().split('/') source_root = meson.current_source_dir().split('/')
build_root = meson.build_root().split('/') build_root = meson.build_root().split('/')
@ -80,11 +94,6 @@ endif
tllist = dependency('tllist', version: '>=1.0.4', fallback: 'tllist') tllist = dependency('tllist', version: '>=1.0.4', fallback: 'tllist')
fcft = dependency('fcft', version: ['>=2.4.0', '<3.0.0'], fallback: 'fcft') fcft = dependency('fcft', version: ['>=2.4.0', '<3.0.0'], fallback: 'fcft')
tic = find_program('tic', native: true, required: get_option('terminfo'))
if tic.found()
add_project_arguments('-DHAVE_TERMINFO', language: 'c')
endif
wayland_protocols_datadir = wayland_protocols.get_pkgconfig_variable('pkgdatadir') wayland_protocols_datadir = wayland_protocols.get_pkgconfig_variable('pkgdatadir')
wscanner = dependency('wayland-scanner', native: true) wscanner = dependency('wayland-scanner', native: true)
@ -221,23 +230,6 @@ executable(
link_with: common, link_with: common,
install: true) install: true)
if tic.found()
terminfo_install_location = get_option('terminfo-install-location')
if terminfo_install_location == ''
terminfo_install_location = join_paths(get_option('datadir'), 'terminfo')
endif
custom_target(
'terminfo',
output: 'f',
input: 'foot.info',
command: [tic, '-x', '-o', '@OUTDIR@', '-e', 'foot,foot-direct', '@INPUT@'],
install: terminfo_install_location != 'disabled',
install_dir: terminfo_install_location)
else
terminfo_install_location = 'disabled'
endif
install_data( install_data(
'foot.desktop', 'foot-server.desktop', 'foot.desktop', 'foot-server.desktop',
install_dir: join_paths(get_option('datadir'), 'applications')) install_dir: join_paths(get_option('datadir'), 'applications'))
@ -251,6 +243,20 @@ if scdoc.found()
subdir('doc') subdir('doc')
endif endif
tic = find_program('tic', native: true, required: get_option('terminfo'))
if tic.found()
custom_target(
'terminfo',
output: 'f',
input: 'foot.info',
command: [tic, '-x', '-o', '@OUTDIR@', '-e', 'foot,foot-direct', '@INPUT@'],
install: true,
install_dir: (terminfo_install_location != 'no'
? terminfo_install_location
: default_terminfo_install_location)
)
endif
subdir('completions') subdir('completions')
subdir('icons') subdir('icons')
@ -259,8 +265,9 @@ summary(
'Documentation': scdoc.found(), 'Documentation': scdoc.found(),
'IME': get_option('ime'), 'IME': get_option('ime'),
'Grapheme clustering': utf8proc.found(), 'Grapheme clustering': utf8proc.found(),
'Terminfo': tic.found(), 'Build terminfo': tic.found(),
'Terminfo install location': terminfo_install_location, 'Default TERM': get_option('default-terminfo'),
'Terminfo custom install location': terminfo_install_location,
}, },
bool_yn: true bool_yn: true
) )

View file

@ -1,10 +1,15 @@
option('docs', type: 'feature', description: 'Build and install documentation (man pages, example foot.ini, readme, changelog, license etc).') option('docs', type: 'feature',
description: 'Build and install documentation (man pages, example foot.ini, readme, changelog, license etc).')
option('ime', type: 'boolean', value: true, description: 'IME (Input Method Editor) support') option('ime', type: 'boolean', value: true,
description: 'IME (Input Method Editor) support')
option('grapheme-clustering', type: 'feature', option('grapheme-clustering', type: 'feature',
description: 'Enables grapheme clustering using libutf8proc. Requires fcft with harfbuzz support to be useful.') description: 'Enables grapheme clustering using libutf8proc. Requires fcft with harfbuzz support to be useful.')
option('terminfo', type: 'feature', description: 'Build terminfo. When disabled, foot\'s terminfo will not be built, and foot will default to \'xterm-256color\' instead of \'foot\'.') option('terminfo', type: 'feature', value: 'enabled', description: 'Build and install foot\'s terminfo files.')
option('default-terminfo', type: 'string', value: 'foot',
description: 'Default value of the "term" option in foot.ini.')
option('terminfo-install-location', type: 'string', description: 'Where to install the foot terminfo files, relative to the installation prefix. If set to \'disabled\', the terminfo files are not installed at all (useful when packaging the terminfo files in a separate package). Defaults to $datadir/terminfo.') option('custom-terminfo-install-location', type: 'string',
description: 'Path to foot\'s terminfo, relative to ${prefix}. If set to anything but “no“, foot will append this value to TERMINFO_DIRS in the client process.')

12
slave.c
View file

@ -289,6 +289,18 @@ slave_spawn(int ptmx, int argc, const char *cwd, char *const *argv,
setenv("TERM", term_env, 1); setenv("TERM", term_env, 1);
setenv("COLORTERM", "truecolor", 1); setenv("COLORTERM", "truecolor", 1);
#if defined(FOOT_TERMINFO_PATH)
const char *terminfo_dirs = getenv("TERMINFO_DIRS");
if (terminfo_dirs != NULL) {
char *updated_terminfo_dirs =
xasprintf("%s:%s", terminfo_dirs, FOOT_TERMINFO_PATH);
setenv("TERMINFO_DIRS", updated_terminfo_dirs, 1);
free(updated_terminfo_dirs);
} else
setenv("TERMINFO_DIRS", FOOT_TERMINFO_PATH, 1);
#endif
char **_shell_argv = NULL; char **_shell_argv = NULL;
char **shell_argv = NULL; char **shell_argv = NULL;