GENRC

NAME
SYNOPSIS
DESCRIPTION
EXAMPLE
OPTIONS
PID SOURCES
ENVIRONMENT
EXIT STATUS
AUTHORS
BUG REPORTS
COPYRIGHT

NAME

genrc - generic system initialization script helper

SYNOPSIS

genrc [-heqv] [-C DIR] [-F PIDFILE] [-P SOURCE] [-c COMMAND] [-g GROUP[,GROUP...]] [-l LIMIT] [-k MODE] [-p PROGRAM] [-s SHELL] [-t SECONDS] [-u USER] [--command=COMMAND] [--create-pidfile=PIDFILE] [--directory=DIR] [--env[=ENVAR[,ENVAR...]]] [--exec] [--group=GROUP[,GROUP...]] [--help] [--kill-mode=MODE] [--no-env] [--no-reload] [--log-err-file=FILE] [--log-facility=FACILITY] [--log-file=FILE] [--log-out-file=FILE] [--log-tag=TAG] [--limit=LIMIT] [--no-reload] [--pid-from=SOURCE] [--pidfile=PIDFILE] [--program=PROGRAM] [--quiet] [--restart-on-exit=[!]STATUS[,STATUS...]] [--restart-on-signal=[!]SIG[,SIG...]] [--sentinel] [--shell=SHELL] [--signal-reload=SIG] [--signal-stop=SIG] [--timeout=SECONDS] [--user=USER] [--usage] [--verbose] { start | stop | restart | reload | status | loghup | wait }

DESCRIPTION

genrc is a generic helper program for writing system initialization scripts. Depending on the operation mode, it starts, stops, reconfigures or displays current status of a specific program.

Operation mode of the program is set by its only mandatory argument. Other program settings are specified via command line options or, if explicitly requested on the command line, environment variables.

The --program option supplies the name of the program, which is used to determine whether the program is already running. If not supplied, the first word (in the shell sense) from COMMAND is used.

If --program is given, but --command is not, its value will be used as the command to run.

Program operation modes are:

start
If given this argument, genrc runs the supplied command. Before, it checks if the program is not already running and refuses to start its second copy if so.

It is supposed that the program to be run will detach from the controlling terminal and continue running in the background (i.e. it is a daemon, in UNIX sense). If it is not the case, use the --sentinel option. With this option, genrc will start the command and become a daemon, controlling the execution of the program. It will exit when the command terminates. Program’s standard output and error will be captured and logged to syslog facility daemon, with priorities info and err, correspondingly. Alternatively, standard streams can be redirected to a file using the --log-file, or to different files, using --log-err-file and --log-out-file options.

If the --create-pidfile=FILENAME option is given together with --sentinel, the PID of the started command will be stored in FILE. The file will be unlinked after the subsidiary command terminates. Unless the --pid-from option is also given, --pid-from=FILE:FILENAME will be assumed.

In sentinel mode, it is possible to restart the program if it terminates with a specific exit code or on a specific signal. This is controlled by the --restart-on-exit and --restart-on-signal options. Use this feature to ensure the service provided by the program won’t get terminated because of hitting a bug or encountering an unforeseen external condition. For example, the following two options make sure that the program will be terminated only if it exits with status 0 or is delivered the SIGTERM or SIGQUIT signal:

--restart-on-exit=’!0’ --restart-on-signal=’!TERM,QUIT’

If restarts are requested, genrc will control how often it has to restart the program using the same algorithm as init (8). Namely, if the program is restarted more than 10 times within two minutes, genrc will disable subsequent restarts for the next 5 minutes. If the --create-pidfile option was used, the PID of the controlling genrc process will be stored in the file during that interval. If the SIGHUP signal is delivered during the sleep interval, the sleep will be broken prematurely and the program restarted again.

status
In status mode genrc verifies if the COMMAND is already running and outputs its status on the standard output. To this effect, it uses an abstraction called PID source, which allows it to determine the PID of the program.

The default PID source is the Linux /proc filesystem (or, if it is not available, the output of ps -efw), which is scanned for the name of the program (as given by --program or --command options).

The source to use can be supplied with the --pid-from option (or the --pidfile option, which is equivalent to --pid-from=FILE). See the section PID SOURCES for a detailed discussion of available sources.

stop
In the stop mode genrc stops the command by sending it SIGTERM (or another signal, as supplied with the --signal-stop option). If the PID source returns multiple PIDs, by default only parent PID is selected. However, genrc can be instructed to signal all PIDs instead (see the a flag in the description of PROC or PS PID source).

After sending the signal, the program will wait for all processes to terminate. If they don’t terminate within 5 seconds, genrc will send the SIGKILL signal and wait another 5 seconds for them to terminate. The timeout can be changed using the --timeout option.

The way to send signals to the program is determined by the -k (--kill-mode) option. If its value is group, both SIGTERM and, if necessary subsequent SIGKILL will be sent to all processes in the process control group. If the value is process, the signal will be sent directly to the process. This is the default. Finally, if the value is mixed, the SIGTERM is sent to the main process, while the subsequent SIGKILL is sent to the control group of the process.

restart
Restarts the program. It is equivalent to running genrc stop immediately followed by genrc start.

reload
Attempts to reload (or reconfigure) the program by sending it the SIGHUP signal (or another signal, as given with the --signal-reload option). The --no-reload or --signal-reload=0 option disables this behavior, making this mode equivalent to genrc restart.

loghup
Locates the parent genrc process that runs the command and sends it the signal instructing it to reopen log files created with --log-file, --log-err-file, and --log-out-file options. This is intended to assist in rotating these files.

Notice, that this mode makes sense only if the command was started using the --sentinel option together with at least one of the above mentioned options.

wait
Waits for the program to terminate. Wait time is specified using the --timeout option and is 5 seconds by default. Exit code is 0 if the program terminated, and 1 on time out.

Use this command verb to wait for the program if it was terminated by some external means.

EXAMPLE

Following is a sample rc.ntpd file for Slackware:

#! /bin/sh
PIDFILE=/var/run/ntpd.pid
exec /sbin/genrc \
--command="/usr/sbin/ntpd -g -p $PIDFILE" \
--no-reload \
--signal-stop=SIGHUP \
--pid-from="FILE:$PIDFILE" "$@"

OPTIONS

-c, --command=COMMAND

Command line to run.

--create-pidfile=NAME

When used together with --sentinel, the PID of the command being run will be stored in file NAME. The --pid-from=FILE:NAME will be assumed, unless the --pid-from is given explicitly (or the GENRC_PID_FROM variable is set).

-C, --directory=DIR

Change to directory DIR.

--env[=ENVAR[,ENVAR...]]

Read missing settings from the environment variables. If a list of variable names is given as argument, only those environment variables will be consulted. Otherwise, all supported variables are used. See the section ENVIRONMENT, for a detailed discussion.

-e, --exec

In sentinel mode, run the command directly via exec(3), instead of using sh -c. Alias: --shell=none.

-F, --pidfile=NAME

Name of the PID file (same as --pid-from=FILE:NAME)

-h, --help

Display a short help list.

-g, --group=GROUP[,GROUP...]

Run program with this GROUP privileges. If the argument is a list of groups, the first group becomes the principal one, and the rest of them supplementary groups. Each GROUP is either a group name or a numeric group number prefixed with a plus sign. Whatever notation is used, the groups must exist in the system group database.

See also the --user option.

-k, --kill-mode=MODE

Specifies how to send termination signal to the main process. MODE is one of group (send termination signal to the process control group), process (send it to the process itself), or mixed (send termination signal to the process, and send subsequent SIGKILL to the program control group). Refer to the description of the stop command above for a detailed discussion of these three modes.

-l, --limit=LIM

Set resource limit. LIM is a resource letter followed by a value. Resource letters are:

c

Core file size (KB).

d

Data size (KB).

f

File size (KB).

l

Locked-in-memory address space (KB).

m

Resident set size (KB).

n

Number of open files.

p

Process priority (nice value), -20..19.

s

Stack size (KB).

t

CPU time (seconds).

u

Number of subprocesses.

v

Virtual memory size (KB).

Their upper-case equivalents enforce limit setting, i.e. the command will be started only if setting the corresponding limit succeeded.

Several limits can be set in one option by concatenating them (with optional whitespace in between).

--log-err-file=FILE

Redirect the command’s stderr to FILE.

--log-facility=FACILITY

Selects syslog facility for use in sentinel mode. Valid arguments are auth, authpriv, cron, daemon, ftp, lpr, mail, user, and local0 through local7. The default is daemon.

--log-file=FILE

Redirect the command’s standard streams to FILE. This option cannot be used together with --log-err-file and --log-out-file.

--log-out-file=FILE

Redirect the command’s stdout to FILE.

--log-tag=TAG

Sets syslog tag for use in sentinel mode.

--no-env

Suppress warnings about environment variables that are set, but ignored. See ENVIRONMENT, for details.

--no-reload

Makes reload equivalent to restart.

-p, --program=PROGRAM

Name of the program to run.

-P, --pid-from=SOURCE

Where to look for PIDs of the running programs.

-q, --quiet

Suppress normal diagnostic messages. This is a counterpart of --verbose (see below). Especially useful with status, when only exit status is needed.

--restart-on-exit=[!]STATUS[,STATUS...]

This option takes effect when used together with --sentinel. If the program terminates with one of status codes listed as the argument to this option, it will be immediately restarted. The exclamation mark at the start of the list inverts the set, e.g. --restart-on-exit=’!0,1’ means restart unless the program exit code is 0 or 1. Note the use of quotation to prevent the ! from being interpreted by the shell.

--restart-on-signal=[!]SIG[,SIG...]

This option takes effect when used together with --sentinel. If the program terminates due to receiving one of the signals from this list, it will be immediately restarted. Each SIG is either a signal number, or a signal name, as listed in signal(7). The SIG prefix can be omitted from the signal name. Names are case-insensitive. Thus, 1, HUP, SIGHUP, and sighup all stand for the same signal.

The exclamation mark at the start of the list complements the signal set, so that e.g. --restart-on-signal=’!TERM,QUIT,INT’ will restart the program unless it terminates on one of the listed signals.

--sentinel

PROGRAM runs in foreground; disconnect from the controlling terminal, start it and run in background until it terminates. The program’s stdout and stderr are sent to the syslog facility daemon, priorities info and err, correspondingly.

The default facility and syslog tag can be changed using the --log-facility and --log-tag options.

See the options --restart-on-exit and --restart-on-signal for details on how to restart the program.

-s, --shell=SHELL

In sentinel mode, use SHELL to run the command, instead of the default /bin/sh. SHELL must support the -c option. Use --shell=none or --exec to run the command directly.

--signal-reload=SIG

Signal to send on reload (default: SIGHUP). Setting it to 0 is equivalent to --no-reload.

--signal-stop=SIG

Signal to send in order to terminate the program (default: SIGTERM).

-t, --timeout=SECONDS

Time to wait for the program to start up or terminate.

To set the two timeouts separately, specify SECONDS as:
start=
N,stop=M

The start and stop parameters can be given in any order, and any of them can be omitted.

--usage

Display a short usage summary.

-u, --user=USER

Run with this user privileges. The argument is either a login name or a numeric UID prefixed with the plus sign. Whatever form is used, it must correspond to a valid user from the system user database.

Unless --group option is also given, the primary and supplementary groups of USER will be used.

--version

Display program version and exit.

-v, --verbose

Print verbose messages (e.g. "Starting PROGNAME"). Additional -v options increase verbosity level. So far, two levels are implemented. -vv giving debugging messages. See also -q (--quiet), above.

PID SOURCES

FILE:FILENAME

Read PID from the file FILENAME.

CONFIG:LANG:FILENAME:FQRN

Name of the PID file is stored in relation FQRN of the configuration file FILENAME, written in language LANG. Recognizable LANG values are:

BIND

ISC BIND configuration file.

DHCPD

ISC DHCPD configuration file.

GIT

Git-style configuration file.

GRECS

GRECS-style configuration file. This is a generalization of a structured configuration file format.

META1

META1 configuration file.

PATH

Configuration specified as fully-qualified keyword-value pairs (similar to .Xdefaults).

GREP:FILE:s/RX/REPL/[FLAGS][;...]

Grep for the first line in FILE that matches RX. If found, modify the matched portion according to REPL and FLAGS. Use the resulting string as the file name and read PID from that file, as if using the FILE source. Several sed expressions can be supplied, separated with semicolons.

PROC[:[EXE][:FLAGS]]

Look for matching program in /proc/PID/*. If EXE is not supplied or empty, the program name from --program will be used. FLAGS are:

a

signal all matching PIDs

c

match entire command line

e

exact match

g

glob pattern match

i

case-insensitive match

p

PCRE match

r

match real executable name (instead of argv0)

x

extended POSIX regexp match (default)

PS[:[EXE][:FLAGS]]

Look for matching program in the output of ps -ef. EXE and FLAGS are as described above.

ENVIRONMENT

Several genrc options have environment variable equivalents. If given the --env option, genrc will consult these variables to supply missing settings. For example, the program name is given by GENRC_COMMAND environment variable. If the --program option is not given, this variable will be consulted.

The following table summarizes the supported environment variables and their corresponding options:

Variable Option

GENRC_COMMAND=COMMAND

--command=COMMAND

GENRC_CREATE_PIDFILE=NAME

--create-pidfile=NAME

GENRC_GROUP=GROUPS

--group=GROUPS

GENRC_KILL_MODE=MODE

--kill-mode=MODE

GENRC_LOG_ERR_FILE=FILE

--log-err-file=FILE

GENRC_LOG_FACILITY=F

--log-facility=F

GENRC_LOG_FILE=FILE

--log-file=FILE

GENRC_LOG_OUT_FILE=FILE

--log-out-file=FILE

GENRC_LOG_TAG=STR

--log-tag=STR

GENRC_PID_FROM=SOURCE

--pid-from=SOURCE

GENRC_PROGRAM=NAME

--program=NAME

GENRC_SENTINEL=1

--sentinel

GENRC_SIGNAL_RELOAD=SIG

--signal-reload=SIG

GENRC_SIGNAL_STOP=SIG

--signal-stop=SIG

GENRC_TIMEOUT=SECONDS

--timeout=SECONDS

GENRC_USER=NAME

--user=NAME

The variables were introduced in the hope that they will improve readability of startup scripts. For instance, the ntpd example from the previous sections using this feature can be rewritten as:

#! /bin/sh
PIDFILE=/var/run/ntpd.pid
export GENRC_COMMAND="/usr/sbin/ntpd -g -p $PIDFILE"
export GENRC_PID_FROM="FILE:$PIDFILE"
exec /sbin/genrc --env --no-reload --signal-stop=SIGHUP "$@"

However, this also can produce hard to diagnose failures. For example, suppose you set the GENRC_USER variable to test something, forget to unset it afterwards, and then restart ntpd using the script above. The program will then run with the privileges of a non-root user and will certainly malfunction.

To diminish the possibility of such errors, environment variables are used only if the --env option is given. This option takes an optional argument, which allows the admin to control which variables will be consulted. The argument is a list of variable names, separated by commas. For example:

genrc --env=GENRC_COMMAND,GENRC_PROGRAM ...

Notice, that no whitespace is allowed on either side of the equals sign.

Environment variables were used by default in versions of genrc up to 1.5.3. To help in upgrade, new versions of the program issue a warning if any of the variables listed above are set and --env option is not given. If you encounter such warnings, you should either update your script to use the --env option, or move all settings from environment variables to command line options.

If, for some reason, you want to retain variable settings without actually using them, use the --no-env option to suppress this warning.

EXIT STATUS

Unless given the status command verb, genrc exits with status 0 on success, and 1 if any errors occurred. With status, exit code 0 indicates that the command is running and 1 means it is not. If unable to determine command status, exit code 2 is returned.

AUTHORS

Sergey Poznyakoff

BUG REPORTS

Report bugs to <gray@gnu.org>.

COPYRIGHT

Copyright © 2018 -- 2025 Sergey Poznyakoff
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law.


Manpage server at man.gnu.org.ua.

Powered by mansrv 1.1