mirror of
https://github.com/troglobit/finit.git
synced 2026-10-08 16:34:45 +07:00
doc: convert the remaining legacy syntax
The block conversion changed the bodies of the reference sections but left every "**Syntax:**" header spelling the line-based format, so each page opened by teaching the format it then stopped using. Six files were missed entirely: runparts, files, capabilities, requirements, runlevels, and switchroot. runparts had no block spelling written down anywhere, though the parser has read `runparts`, `runparts-progress`, and `runparts-sysv` all along. tty gains a table per variant. Its three syntax lines carried nine positional fields between them, which no longer describes anything the parser accepts. Fixes #148 Signed-off-by: Joachim Wiberg <troglobit@gmail.com>
This commit is contained in:
+9
-9
@@ -242,16 +242,16 @@ Composition
|
||||
-----------
|
||||
|
||||
The `pid/` conditions are generated by the Finit `pidfile.so` plugin and
|
||||
composed from a service's `name:` and `:id`. By default the basename of
|
||||
the daemon and the empty string.
|
||||
composed from a service's block title and its `:id`. By default the
|
||||
basename of the daemon and the empty string.
|
||||
|
||||
| **service** | **condition** |
|
||||
|----------------------------------------------------|------------------|
|
||||
| /sbin/foo | pid/foo |
|
||||
| /sbin/bar -p /run/baz.pid | pid/bar |
|
||||
| name:lxc :foo lxc-start -n foo -p /run/lxc/foo.pid | pid/lxc:foo |
|
||||
| /usr/bin/dbus-daemon | pid/dbus-daemon |
|
||||
| :222 dropbear -p 222 | pid/dropbear:222 |
|
||||
| **service** | **condition** |
|
||||
|-------------------------------------------------------------------|------------------|
|
||||
| `service { command = "/sbin/foo" }` | pid/foo |
|
||||
| `service { command = "/sbin/bar -p /run/baz.pid" }` | pid/bar |
|
||||
| `service lxc:foo { command = "lxc-start -n foo -p /run/lxc/foo.pid" }` | pid/lxc:foo |
|
||||
| `service { command = "/usr/bin/dbus-daemon" }` | pid/dbus-daemon |
|
||||
| `service dropbear:222 { command = "dropbear -p 222" }` | pid/dropbear:222 |
|
||||
|
||||
The condition is asserted when `pidfile.so` receives an inotify event
|
||||
for a file matching `/run/*.pid`, `/run/**/*.pid`, or `/run/**/pid`,
|
||||
|
||||
+41
-31
@@ -16,14 +16,17 @@ which is the same approach used by other modern service managers like dinit.
|
||||
|
||||
## Basic Usage
|
||||
|
||||
Capabilities are specified using the `caps:` directive in service configuration:
|
||||
Capabilities are specified with the `capabilities` key, alias `caps`:
|
||||
|
||||
```conf
|
||||
service [2345] name:nginx \
|
||||
@www-data:www-data \
|
||||
caps:^cap_net_bind_service \
|
||||
/usr/sbin/nginx -g 'daemon off;' \
|
||||
-- Web server
|
||||
service nginx {
|
||||
description = "Web server"
|
||||
runlevel = "2345"
|
||||
user = "www-data"
|
||||
group = "www-data"
|
||||
capabilities = { "^cap_net_bind_service" }
|
||||
command = "/usr/sbin/nginx -g 'daemon off;'"
|
||||
}
|
||||
```
|
||||
|
||||
This example allows nginx to bind to privileged ports (like 80 and 443) while
|
||||
@@ -52,7 +55,7 @@ with the following prefixes:
|
||||
Multiple capabilities can be specified as a comma-separated list:
|
||||
|
||||
```conf
|
||||
caps:^cap_net_raw,^cap_net_admin,^cap_net_bind_service
|
||||
capabilities = { "^cap_net_raw", "^cap_net_admin", "^cap_net_bind_service" }
|
||||
```
|
||||
|
||||
## Common Use Cases
|
||||
@@ -62,10 +65,13 @@ caps:^cap_net_raw,^cap_net_admin,^cap_net_bind_service
|
||||
Allow a web server to bind to ports 80 and 443 without running as root:
|
||||
|
||||
```conf
|
||||
service [2345] name:webserver \
|
||||
@www-data:www-data \
|
||||
caps:^cap_net_bind_service \
|
||||
/usr/sbin/nginx -g 'daemon off;'
|
||||
service webserver {
|
||||
runlevel = "2345"
|
||||
user = "www-data"
|
||||
group = "www-data"
|
||||
capabilities = { "^cap_net_bind_service" }
|
||||
command = "/usr/sbin/nginx -g 'daemon off;'"
|
||||
}
|
||||
```
|
||||
|
||||
### Network Monitoring (Raw Sockets)
|
||||
@@ -73,10 +79,12 @@ service [2345] name:webserver \
|
||||
Allow packet capture without root privileges:
|
||||
|
||||
```conf
|
||||
service [2345] name:tcpdump \
|
||||
@tcpdump \
|
||||
caps:^cap_net_raw,^cap_net_admin \
|
||||
/usr/sbin/tcpdump -i eth0 -w /var/log/capture.pcap
|
||||
service tcpdump {
|
||||
runlevel = "2345"
|
||||
user = "tcpdump"
|
||||
capabilities = { "^cap_net_raw", "^cap_net_admin" }
|
||||
command = "/usr/sbin/tcpdump -i eth0 -w /var/log/capture.pcap"
|
||||
}
|
||||
```
|
||||
|
||||
### NTP Daemon (System Time)
|
||||
@@ -84,10 +92,12 @@ service [2345] name:tcpdump \
|
||||
Allow time synchronization without full root:
|
||||
|
||||
```conf
|
||||
service [2345] name:ntpd \
|
||||
@ntp \
|
||||
caps:^cap_sys_time,^cap_sys_nice \
|
||||
/usr/sbin/ntpd -n
|
||||
service ntpd {
|
||||
runlevel = "2345"
|
||||
user = "ntp"
|
||||
capabilities = { "^cap_sys_time", "^cap_sys_nice" }
|
||||
command = "/usr/sbin/ntpd -n"
|
||||
}
|
||||
```
|
||||
|
||||
## Available Capabilities
|
||||
@@ -116,9 +126,9 @@ Common capabilities include (see `man 7 capabilities` for the complete list):
|
||||
- Don't grant `cap_sys_admin` unless absolutely necessary
|
||||
|
||||
2. **Specify a user (preferably non-root)**
|
||||
- The `@user` directive is **required** for `caps:` to take effect
|
||||
- For ambient capabilities (`^`), use a non-root user (not `@root`)
|
||||
- Example: `@www-data`, `@nginx`, `@tcpdump`
|
||||
- The `user` setting is **required** for `capabilities` to take effect
|
||||
- For ambient capabilities (`^`), use a non-root user (not `"root"`)
|
||||
- Example: `user = "www-data"`, `user = "nginx"`, `user = "tcpdump"`
|
||||
|
||||
3. **Use ambient capabilities (`^`)**
|
||||
- The `^` prefix ensures capabilities survive exec()
|
||||
@@ -163,17 +173,17 @@ ps -o user,pid,cmd -p $(pidof nginx)
|
||||
|
||||
## Limitations
|
||||
|
||||
- The `caps:` directive requires `@user` to be specified for it to take effect
|
||||
- Without `@user`, the service runs as root with full capabilities and
|
||||
the `caps:` configuration is silently ignored
|
||||
- You can use `@root` with `caps:`, but see below about ambient capabilities
|
||||
- `capabilities` requires `user` to be set for it to take effect
|
||||
- Without `user`, the service runs as root with full capabilities and
|
||||
the `capabilities` list is silently ignored
|
||||
- You can use `user = "root"`, but see below about ambient capabilities
|
||||
- For ambient capabilities (`^`, recommended), the user **must be non-root**
|
||||
- Using `@root` with `caps:^...` will not work effectively, as ambient
|
||||
- Using `user = "root"` with `^` capabilities will not work effectively, as ambient
|
||||
capabilities are only added to the effective set when euid ≠ 0
|
||||
- Use inheritable (`%`) or bounding (`!`) capabilities with `@root` if needed
|
||||
- Services without `caps:` use standard privilege dropping:
|
||||
- Services with `@user` (non-root) have no special capabilities
|
||||
- Services without `@user` run as root with full capabilities
|
||||
- Use inheritable (`%`) or bounding (`!`) capabilities with `user = "root"` if needed
|
||||
- Services without `capabilities` use standard privilege dropping:
|
||||
- Services with a non-root `user` have no special capabilities
|
||||
- Services without `user` run as root with full capabilities
|
||||
- Some very old binaries may not work correctly with ambient capabilities
|
||||
- File system capabilities are not managed by Finit (use `setcap` for that)
|
||||
|
||||
|
||||
+3
-3
@@ -180,7 +180,7 @@ document [Finit Services](../service.md).
|
||||
Alternate finit.d/
|
||||
------------------
|
||||
|
||||
**Syntax:** `rcsd /path/to/finit.d`
|
||||
**Syntax:** `rcsd = "/path/to/finit.d"`
|
||||
|
||||
The Finit rcS.d directory is set at compile time with:
|
||||
|
||||
@@ -194,7 +194,7 @@ configurations, starting with the kernel command line option:
|
||||
This file in turn can use the `rcsd` directive to tell Finit to use
|
||||
another set of .conf files, e.g.:
|
||||
|
||||
rcsd /etc/factory.d
|
||||
rcsd = "/etc/factory.d"
|
||||
|
||||
> [!NOTE]
|
||||
> This directive is only available from the top-level bootstrap .conf
|
||||
@@ -203,6 +203,6 @@ another set of .conf files, e.g.:
|
||||
Including Finit Configs
|
||||
------------------------
|
||||
|
||||
**Syntax:** `include <CONF>`
|
||||
**Syntax:** `include("CONF")`
|
||||
|
||||
Include another configuration file. Absolute path required.
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
General Logging
|
||||
===============
|
||||
|
||||
**Syntax:** `log size:200k count:5`
|
||||
**Syntax:** `log { size = 200k count = 5 }`
|
||||
|
||||
Log rotation for run/task/services using the `log` sub-option with
|
||||
redirection to a log file. Global setting, applies to all services.
|
||||
|
||||
The size can be given as bytes, without a specifier, or in `k`, `M`,
|
||||
or `G`, e.g. `size:10M`, or `size:3G`. A value of `size:0` disables
|
||||
or `G`, e.g. `size = 10M`, or `size = 3G`. A value of `size = 0` disables
|
||||
log rotation. The default is `200k`.
|
||||
|
||||
The count value is recommended to be between 1-5, with a default 5.
|
||||
|
||||
+21
-18
@@ -66,7 +66,7 @@ least the loopback interface is brought up.
|
||||
Runlevel Configuration
|
||||
----------------------
|
||||
|
||||
**Syntax:** `runlevel <N>`
|
||||
**Syntax:** `runlevel = N`
|
||||
|
||||
The system runlevel to go to after bootstrap (S) has completed. `N` is
|
||||
the runlevel number 0-9, where 6 is reserved for reboot and 0 for halt.
|
||||
@@ -84,7 +84,7 @@ Finit disables networking in this mode.
|
||||
Networking
|
||||
----------
|
||||
|
||||
**Syntax:** `network <PATH>`
|
||||
**Syntax:** `network = "PATH"`
|
||||
|
||||
Script or program to bring up networking, with optional arguments.
|
||||
|
||||
@@ -98,7 +98,7 @@ Debian, Ubuntu, Linux Mint, or an embedded BusyBox system.
|
||||
System Hostname
|
||||
---------------
|
||||
|
||||
**Syntax:** `host <NAME>`, or `hostname <NAME>`
|
||||
**Syntax:** `hostname = "NAME"`
|
||||
|
||||
Set system hostname to NAME, unless `/etc/hostname` exists in which case
|
||||
the contents of that file is used.
|
||||
@@ -111,10 +111,16 @@ Deprecated. We recommend using `/etc/hostname` instead.
|
||||
Kernel Modules
|
||||
--------------
|
||||
|
||||
**Syntax:** `module <MODULE> [ARGS]`
|
||||
**Syntax:** `modules = { "MODULE [ARGS]", ... }`, alias `mod`
|
||||
|
||||
Load a kernel module, with optional arguments. Similar to `insmod`
|
||||
command line tool.
|
||||
Load kernel modules, each with optional arguments. Similar to the
|
||||
`insmod` command line tool.
|
||||
|
||||
modules = { "button", "evdev", "softdog" }
|
||||
|
||||
> [!NOTE]
|
||||
> A list cannot hold comments; the lexer reads the entries after a `#`
|
||||
> regardless. Put commented-out candidates above the list.
|
||||
|
||||
Deprecated, there is both a `modules-load.so` and a `modprobe.so` plugin
|
||||
that can handle module loading better. The former supports loading from
|
||||
@@ -130,9 +136,9 @@ BusyBox mdev tool, add to `/etc/mdev.conf`:
|
||||
Resource Limits
|
||||
---------------
|
||||
|
||||
**Syntax:** `rlimit [hard|soft] RESOURCE <LIMIT|unlimited>`
|
||||
**Syntax:** `rlimit { RESOURCE = LIMIT }`, with `soft.` or `hard.` prefix
|
||||
|
||||
Set the hard or soft limit for a resource, or both if that argument is
|
||||
Set the hard or soft limit for a resource, or both if the prefix is
|
||||
omitted. `RESOURCE` is the lower-case `RLIMIT_` string constants from
|
||||
`setrlimit(2)`, without prefix. E.g. to set `RLIMIT_CPU`, use `cpu`.
|
||||
|
||||
@@ -142,14 +148,11 @@ or the kernel `/proc/PID/limits` file, for details. Finit versions
|
||||
before v3.1 used `infinity` for `unlimited`, which is still supported,
|
||||
albeit deprecated.
|
||||
|
||||
# No process is allowed more than 8MB of address space
|
||||
rlimit hard as 8388608
|
||||
|
||||
# Core dumps may be arbitrarily large
|
||||
rlimit soft core infinity
|
||||
|
||||
# CPU limit for all services, soft & hard = 10 sec
|
||||
rlimit cpu 10
|
||||
rlimit {
|
||||
hard.as = 8388608 # no more than 8MB of address space
|
||||
soft.core = unlimited # core dumps may be arbitrarily large
|
||||
cpu = 10 # soft & hard = 10 sec
|
||||
}
|
||||
|
||||
`rlimit` can be set globally, in `/etc/finit.conf`, or locally per
|
||||
each `/etc/finit.d/*.conf` read. I.e., a set of task/run/service
|
||||
@@ -158,7 +161,7 @@ stanzas can share the same rlimits if they are in the same .conf.
|
||||
Miscellaneous Settings
|
||||
----------------------
|
||||
|
||||
**Syntax:** `reboot-delay <0-60>`
|
||||
**Syntax:** `reboot-delay = 0-60`
|
||||
|
||||
Optional delay at reboot (or shutdown or halt) to allow kernel
|
||||
filesystem threads to complete after calling `sync(2)` before
|
||||
@@ -176,7 +179,7 @@ sync(2) has been called, twice.
|
||||
> writing; it can actually take a short time before all the blocks are
|
||||
> finally written.
|
||||
|
||||
**Syntax:** `reboot-watchdog <on|off|true|false|1|0>`
|
||||
**Syntax:** `reboot-watchdog = true|false`
|
||||
|
||||
Controls whether the system should reboot via the watchdog timer (WDT)
|
||||
or directly via the SoC/kernel. When enabled, Finit will:
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
Run-parts Scripts
|
||||
-----------------
|
||||
|
||||
**Syntax:** `runparts [progress] [sysv] <DIR>`
|
||||
**Syntax:** `runparts = "DIR"`
|
||||
|
||||
Call [run-parts(8)][] on `DIR` to run start scripts. All executable
|
||||
files in the directory are called, in alphabetic order. The scripts in
|
||||
@@ -14,9 +14,10 @@ whatever the next runlevel is set to be (default 2). E.g., generate a
|
||||
|
||||
**Options:**
|
||||
|
||||
- `progress`: display the progress of each script being executed
|
||||
- `sysv`: run only SysV style scripts, i.e., `SNNfoo`, or `KNNbar`,
|
||||
where `NN` is a number (0-99).
|
||||
- `runparts-progress = true`: display the progress of each script being
|
||||
executed
|
||||
- `runparts-sysv = true`: run only SysV style scripts, i.e., `SNNfoo`,
|
||||
or `KNNbar`, where `NN` is a number (0-99).
|
||||
|
||||
If global debug mode is enabled, the `runparts` program is also called
|
||||
with the debug flag.
|
||||
|
||||
@@ -43,8 +43,8 @@ like this:
|
||||
service bar { notify = "s6" command = "bar" }
|
||||
service qux { notify = "none" command = "qux" }
|
||||
|
||||
The `notify:none` syntax is for completeness in systems which run in
|
||||
`readiness pid` mode (default). Services declared with `notify:none`
|
||||
The `notify = "none"` setting is for completeness in systems which run in
|
||||
`readiness pid` mode (default). Services declared with `notify = "none"`
|
||||
will transition to ready as soon as Finit has started them, e.g.,
|
||||
`service/qux/ready`.
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
Services
|
||||
========
|
||||
|
||||
**Syntax:** `service [LVLS] <COND> /path/to/daemon ARGS -- Optional description`
|
||||
**Syntax:** `service NAME { command = "/path/to/daemon ARGS" }`
|
||||
|
||||
Service, or daemon, to be monitored and automatically restarted if it
|
||||
exits prematurely. Finit tries to restart services that die, by default
|
||||
|
||||
+2
-2
@@ -9,7 +9,7 @@ from a serialized boot process.
|
||||
SysV Init Scripts
|
||||
-----------------
|
||||
|
||||
**Syntax:** `sysv [LVLS] <COND> /path/to/init-script -- Optional description`
|
||||
**Syntax:** `sysv NAME { command = "/path/to/init-script" }`
|
||||
|
||||
> `<COND>` is described in the [Services](services.md) section.
|
||||
|
||||
@@ -45,7 +45,7 @@ making it perfect for most scenarios.
|
||||
For syntax details, see the [Run-parts Scripts](runparts.md) section.
|
||||
Here is an example take from a Debian installation:
|
||||
|
||||
runparts /etc/rc2.d
|
||||
runparts = "/etc/rc2.d"
|
||||
|
||||
Files in these directories are usually named `SNNfoo` and `KNNfoo`,
|
||||
which Finit knows about and automatically appends the correct argument:
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
run (sequence)
|
||||
--------------
|
||||
|
||||
**Syntax:** `run [LVLS] <COND> /path/to/cmd ARGS -- Optional description`
|
||||
**Syntax:** `run NAME { command = "/path/to/cmd ARGS" }`
|
||||
|
||||
> `<COND>` is described in the [Services](services.md) section.
|
||||
|
||||
@@ -31,7 +31,7 @@ also the `--quiet` and `--batch` options.
|
||||
task (parallel)
|
||||
---------------
|
||||
|
||||
**Syntax:** `task [LVLS] <COND> /path/to/cmd ARGS -- Optional description`
|
||||
**Syntax:** `task NAME { command = "/path/to/cmd ARGS" }`
|
||||
|
||||
> `<COND>` is described in the [Services](services.md) section.
|
||||
|
||||
@@ -93,7 +93,7 @@ The firewall rules are created once. The `exec-stop-post` script runs when
|
||||
entering runlevel 0 (halt) or 6 (reboot), or on explicit stop.
|
||||
|
||||
> [!NOTE]
|
||||
> The `remain:yes` option is not supported for bootstrap-only tasks
|
||||
> (tasks with only runlevel S). Bootstrap tasks are deleted immediately
|
||||
> after completion, and their `post:` scripts never run. A warning is
|
||||
> logged if `remain:yes` is used on such tasks.
|
||||
> The `remain-after-exit` option is not supported for bootstrap-only
|
||||
> tasks (tasks with only runlevel S). Bootstrap tasks are deleted
|
||||
> immediately after completion, and their `exec-stop-post` scripts never
|
||||
> run. A warning is logged if `remain-after-exit` is used on such tasks.
|
||||
|
||||
+24
-8
@@ -1,16 +1,32 @@
|
||||
TTYs and Consoles
|
||||
=================
|
||||
|
||||
**Syntax:** `tty [LVLS] <COND> DEV [BAUD] [noclear] [nowait] [nologin] [TERM]`
|
||||
`tty [LVLS] <COND> CMD <ARGS> [noclear] [nowait]`
|
||||
`tty [LVLS] <COND> [notty] [rescue]`
|
||||
**Syntax:** `tty NAME { device = DEV }` -- built-in getty
|
||||
`tty NAME { command = "CMD ARGS" }` -- external getty
|
||||
`tty NAME { notty = true }`, or `{ rescue = true }` -- bare shell, no device
|
||||
|
||||
The first variant of this option uses the built-in getty on the given
|
||||
TTY device DEV, in the given runlevels. DEV may be the special keyword
|
||||
`@console`, which is expanded from `/sys/class/tty/console/active`,
|
||||
useful on embedded systems.
|
||||
The block title NAME is what `initctl` shows. The three variants differ
|
||||
in what they open: `device` runs the built-in getty on that TTY, and DEV
|
||||
may be the special keyword `@console`, expanded from
|
||||
`/sys/class/tty/console/active`, useful on embedded systems. `command`
|
||||
hands the TTY to an external getty. `notty` opens nothing at all.
|
||||
|
||||
The default baud rate is 0, i.e., keep kernel default.
|
||||
Settings common to all three:
|
||||
|
||||
| Setting | Alias | Description |
|
||||
|---|---|---|
|
||||
| `runlevel` | | Runlevels to run in, e.g. `"12345"` |
|
||||
| `conditions` | `cond` | Conditions to wait for |
|
||||
| `noclear` | | Do not clear the TTY after each session |
|
||||
| `nowait` | | Do not wait for Enter before the login prompt |
|
||||
| `nologin` | | Skip login, give a shell straight away |
|
||||
|
||||
The `device` variant takes two more:
|
||||
|
||||
| Setting | Description |
|
||||
|---|---|
|
||||
| `baud` | Baud rate, default 0, i.e., keep kernel default |
|
||||
| `term` | `$TERM` value, e.g. `"vt220"` |
|
||||
|
||||
> The `tty` stanza inherits runlevel, condition (and other feature)
|
||||
> parsing from the `service` stanza. So TTYs can run in one or many
|
||||
|
||||
+103
-49
@@ -10,69 +10,126 @@ See the [contrib/][contrib] directory on GitHub for examples, or take a
|
||||
peek at systems using Finit, like [Infix OS][infix] and [myLinux][].
|
||||
|
||||
> [!TIP]
|
||||
> As of Finit v4.4, `.conf` lines can be broken up using the standard UNIX
|
||||
> continuation character (`\`), trailing comments are also supported. The
|
||||
> latter means you must escape any hashes used in directives and descriptions
|
||||
> (`\#`). For more on this and examples, see the [finit.conf(5)][] manual or
|
||||
> the [Configuration](config/index.md) section.
|
||||
> A block spans as many lines as it needs, so no continuation character is
|
||||
> called for. For the full syntax, see the [finit.conf(5)][] manual or the
|
||||
> [Configuration](config/index.md) section.
|
||||
|
||||
```ApacheConf
|
||||
# Fallback if /etc/hostname is missing
|
||||
host default
|
||||
hostname = "default"
|
||||
|
||||
# Runlevel to start after bootstrap, 'S', default: 2
|
||||
#runlevel 2
|
||||
#runlevel = 2
|
||||
|
||||
# Support for setting global environment variables, using foo=bar syntax
|
||||
# be careful though with variables like PATH, SHELL, LOGNAME, etc.
|
||||
#PATH=/usr/bin:/bin:/usr/sbin:/sbin
|
||||
# Global environment variables, be careful though with variables like
|
||||
# PATH, SHELL, LOGNAME, etc.
|
||||
#environment {
|
||||
# PATH = "/usr/bin:/bin:/usr/sbin:/sbin"
|
||||
#}
|
||||
|
||||
# Max file size for each log file: 100 kiB, rotate max 4 copies:
|
||||
# log => log.1 => log.2.gz => log.3.gz => log.4.gz
|
||||
log size=100k count=4
|
||||
log {
|
||||
size = 100k
|
||||
count = 4
|
||||
}
|
||||
|
||||
# Services to be monitored and respawned as needed
|
||||
service [S12345] env:-/etc/conf.d/watchdog watchdog $WATCHDOG_OPTS $WATCHDOG_DEV -- System watchdog daemon
|
||||
service [S12345] env:-/etc/conf.d/syslog syslogd -n $SYSLOGD_OPTS -- System log daemon
|
||||
service [S12345] <pid/syslogd> env:-/etc/conf.d/klogd klogd -n $KLOGD_OPTS -- Kernel log daemon
|
||||
service [2345] env:-/etc/conf.d/lldpd lldpd -d $LLDPD_OPTS -- LLDP daemon (IEEE 802.1ab)
|
||||
service watchdog {
|
||||
description = "System watchdog daemon"
|
||||
runlevel = "S12345"
|
||||
envfile = "-/etc/conf.d/watchdog"
|
||||
command = "watchdog $WATCHDOG_OPTS $WATCHDOG_DEV"
|
||||
}
|
||||
service syslogd {
|
||||
description = "System log daemon"
|
||||
runlevel = "S12345"
|
||||
envfile = "-/etc/conf.d/syslog"
|
||||
command = "syslogd -n $SYSLOGD_OPTS"
|
||||
}
|
||||
service klogd {
|
||||
description = "Kernel log daemon"
|
||||
runlevel = "S12345"
|
||||
conditions = { "pid/syslogd" }
|
||||
envfile = "-/etc/conf.d/klogd"
|
||||
command = "klogd -n $KLOGD_OPTS"
|
||||
}
|
||||
service lldpd {
|
||||
description = "LLDP daemon (IEEE 802.1ab)"
|
||||
runlevel = "2345"
|
||||
envfile = "-/etc/conf.d/lldpd"
|
||||
command = "lldpd -d $LLDPD_OPTS"
|
||||
}
|
||||
|
||||
# The BusyBox ntpd does not use syslog when running in the foreground
|
||||
# So we use this trick to redirect stdout/stderr to a log file. The
|
||||
# log file is rotated with the above settings. The condition declares
|
||||
# a dependency on a system default route (gateway) to be set. A single
|
||||
# <!> at the beginning means ntpd does not respect SIGHUP for restart.
|
||||
service [2345] log:/var/log/ntpd.log <!net/route/default> ntpd -n -l -I eth0 -- NTP daemon
|
||||
# a dependency on a system default route (gateway) to be set. ntpd
|
||||
# does not respect SIGHUP, so Finit restarts it on reload instead.
|
||||
service ntpd {
|
||||
description = "NTP daemon"
|
||||
runlevel = "2345"
|
||||
conditions = { "net/route/default" }
|
||||
reload-signal = "none"
|
||||
log { file = "/var/log/ntpd.log" }
|
||||
command = "ntpd -n -l -I eth0"
|
||||
}
|
||||
|
||||
# For multiple instances of the same service, add :ID somewhere between
|
||||
# the service/run/task keyword and the command.
|
||||
service :80 [2345] merecat -n -p 80 /var/www -- Web server
|
||||
service :8080 [2345] merecat -n -p 8080 /var/www -- Old web server
|
||||
# For multiple instances of the same service, add :ID to the block title.
|
||||
service merecat:80 {
|
||||
description = "Web server"
|
||||
runlevel = "2345"
|
||||
command = "merecat -n -p 80 /var/www"
|
||||
}
|
||||
service merecat:8080 {
|
||||
description = "Old web server"
|
||||
runlevel = "2345"
|
||||
command = "merecat -n -p 8080 /var/www"
|
||||
}
|
||||
|
||||
# Alternative method instead of below runparts, can also use /etc/rc.local
|
||||
#sysv [S] /etc/init.d/keyboard-setup -- Setting up preliminary keymap
|
||||
#sysv [S] /etc/init.d/acpid -- Starting ACPI Daemon
|
||||
#task [S] /etc/init.d/kbd -- Preparing console
|
||||
#sysv keyboard-setup {
|
||||
# description = "Setting up preliminary keymap"
|
||||
# runlevel = "S"
|
||||
# command = "/etc/init.d/keyboard-setup"
|
||||
#}
|
||||
|
||||
# Hidden from boot progress, using empty `--` description
|
||||
#sysv [S] /etc/init.d/keyboard-setup --
|
||||
#sysv [S] /etc/init.d/acpid --
|
||||
#task [S] /etc/init.d/kbd --
|
||||
# Hidden from boot progress, using an empty description
|
||||
#sysv acpid {
|
||||
# description = ""
|
||||
# runlevel = "S"
|
||||
# command = "/etc/init.d/acpid"
|
||||
#}
|
||||
|
||||
# Run start scripts from this directory
|
||||
# runparts /etc/start.d
|
||||
#runparts = "/etc/start.d"
|
||||
|
||||
# Virtual consoles run BusyBox getty, keep kernel default speed
|
||||
tty [12345] /sbin/getty -L 0 /dev/tty1 linux nowait noclear
|
||||
tty [2345] /sbin/getty -L 0 /dev/tty2 linux nowait noclear
|
||||
tty [2345] /sbin/getty -L 0 /dev/tty3 linux nowait noclear
|
||||
tty tty1 {
|
||||
runlevel = "12345"
|
||||
command = "/sbin/getty -L 0 /dev/tty1 linux"
|
||||
nowait = true
|
||||
noclear = true
|
||||
}
|
||||
tty tty2 {
|
||||
runlevel = "2345"
|
||||
command = "/sbin/getty -L 0 /dev/tty2 linux"
|
||||
nowait = true
|
||||
noclear = true
|
||||
}
|
||||
tty tty3 {
|
||||
runlevel = "2345"
|
||||
command = "/sbin/getty -L 0 /dev/tty3 linux"
|
||||
nowait = true
|
||||
noclear = true
|
||||
}
|
||||
|
||||
# Use built-in getty for serial port and USB serial
|
||||
#tty [12345] /dev/ttyAMA0 noclear nowait
|
||||
#tty [12345] /dev/ttyUSB0 noclear
|
||||
#tty ttyAMA0 { runlevel = "12345" device = "/dev/ttyAMA0" noclear = true nowait = true }
|
||||
#tty ttyUSB0 { runlevel = "12345" device = "/dev/ttyUSB0" noclear = true }
|
||||
|
||||
# Just give me a shell, I need to debug this embedded system!
|
||||
#tty [12345] console noclear nologin
|
||||
#tty console { runlevel = "12345" device = "@console" noclear = true nologin = true }
|
||||
```
|
||||
|
||||
The `service` stanza, as well as `task`, `run` and others are described in
|
||||
@@ -82,21 +139,18 @@ Here's a quick overview of some of the most common components needed to start
|
||||
a UNIX daemon:
|
||||
|
||||
```
|
||||
service [LVLS] <COND> log env:[-]/etc/default/daemon daemon ARGS -- Example daemon
|
||||
^ ^ ^ ^ ^ ^ ^ ^
|
||||
| | | | | | | `---------- Optional description
|
||||
| | | | | | `------------------ Daemon arguments
|
||||
| | | | | `------------------------- Path to daemon
|
||||
| | | | `---------------------------------------------------- Optional env. file
|
||||
| | | `-------------------------------------------------------- Redirect output to log
|
||||
| | `--------------------------------------------------------------- Optional conditions
|
||||
| `---------------------------------------------------------------------- Optional Runlevels
|
||||
`------------------------------------------------------------------------------ Supervised program (daemon)
|
||||
service NAME { <-- Supervised program (daemon)
|
||||
description = "Example daemon" <-- Optional description
|
||||
runlevel = "2345" <-- Optional runlevels
|
||||
conditions = { "net/route/default" } <-- Optional conditions
|
||||
envfile = "-/etc/default/daemon" <-- Optional env. file
|
||||
log { } <-- Redirect output to log
|
||||
command = "daemon ARGS" <-- Path to daemon, and its arguments
|
||||
}
|
||||
```
|
||||
|
||||
Some components are optional: runlevel(s), condition(s) and description,
|
||||
making it easy to create simple start scripts and still possible for more
|
||||
advanced uses as well:
|
||||
Only `command` is required, which makes simple cases short while leaving
|
||||
room for more advanced uses:
|
||||
|
||||
service sshd {
|
||||
command = "/usr/sbin/sshd -D"
|
||||
|
||||
+24
-12
@@ -18,9 +18,9 @@ waits for user input before handing over to `/bin/login`, which is
|
||||
responsible for handling the actual authentication.
|
||||
|
||||
```conf
|
||||
tty [12345] /dev/tty1 nowait linux
|
||||
tty [12345] /dev/ttyAMA0 noclear vt100
|
||||
tty [12345] /sbin/getty -L /dev/ttyAMA0 vt100
|
||||
tty tty1 { runlevel = "12345" device = "/dev/tty1" term = "linux" nowait = true }
|
||||
tty ttyAMA0 { runlevel = "12345" device = "/dev/ttyAMA0" term = "vt100" noclear = true }
|
||||
tty getty { runlevel = "12345" command = "/sbin/getty -L /dev/ttyAMA0 vt100" }
|
||||
```
|
||||
|
||||
Users of embedded systems may want to enable automatic serial console
|
||||
@@ -29,7 +29,7 @@ system uses `ttyS0`, `ttyAMA0`, `ttyMXC0`, or anything else. Finit
|
||||
figures it out by querying sysfs: `/sys/class/tty/console/active`.
|
||||
|
||||
```conf
|
||||
tty [12345] @console linux noclear
|
||||
tty console { runlevel = "12345" device = "@console" term = "linux" noclear = true }
|
||||
```
|
||||
|
||||
Notice the optional `noclear`, `nowait`, and `nologin` flags. The
|
||||
@@ -86,8 +86,17 @@ the condition `<hw/model/foo>` when starting other scripts. Here is an
|
||||
example:
|
||||
|
||||
```
|
||||
run [S] /path/to/ident --
|
||||
task [2] <hw/model/foo> /path/to/foo-init -- Initializing Foo board
|
||||
run ident {
|
||||
description = ""
|
||||
runlevel = "S"
|
||||
command = "/path/to/ident"
|
||||
}
|
||||
task foo-init {
|
||||
description = "Initializing Foo board"
|
||||
runlevel = "2"
|
||||
conditions = { "hw/model/foo" }
|
||||
command = "/path/to/foo-init"
|
||||
}
|
||||
```
|
||||
|
||||
> [!TIP]
|
||||
@@ -141,17 +150,20 @@ required privileges instead of running as root. This improves security by
|
||||
following the principle of least privilege.
|
||||
|
||||
```conf
|
||||
service [2345] name:nginx \
|
||||
www-data:www-data \
|
||||
caps:^cap_net_bind_service \
|
||||
/usr/sbin/nginx -g 'daemon off;'
|
||||
service nginx {
|
||||
runlevel = "2345"
|
||||
user = "www-data"
|
||||
group = "www-data"
|
||||
capabilities = { "^cap_net_bind_service" }
|
||||
command = "/usr/sbin/nginx -g 'daemon off;'"
|
||||
}
|
||||
```
|
||||
|
||||
In this example, nginx runs as the unprivileged `www-data` user but retains
|
||||
the ability to bind to privileged ports (80, 443) through the
|
||||
`cap_net_bind_service` capability.
|
||||
|
||||
The `caps:` directive uses the IAB (Inheritable, Ambient, Bounding) format:
|
||||
The `capabilities` list uses the IAB (Inheritable, Ambient, Bounding) format:
|
||||
- `^` = Ambient (recommended) - capabilities survive exec()
|
||||
- `%` = Inheritable only - requires file capabilities
|
||||
- `!` = Bounding - block from acquiring capability
|
||||
@@ -159,7 +171,7 @@ The `caps:` directive uses the IAB (Inheritable, Ambient, Bounding) format:
|
||||
Multiple capabilities can be specified as comma-separated:
|
||||
|
||||
```conf
|
||||
caps:^cap_net_raw,^cap_net_admin,!cap_sys_admin
|
||||
capabilities = { "^cap_net_raw", "^cap_net_admin", "!cap_sys_admin" }
|
||||
```
|
||||
|
||||
See the [Linux Capabilities](config/capabilities.md) section for detailed
|
||||
|
||||
+1
-1
@@ -71,7 +71,7 @@ For your convenience a set of *optional* plugins are available:
|
||||
comment character, `#`, or `;`, is skipped.
|
||||
|
||||
Modules are by default loaded in runlevel `S` using the `task` stanza.
|
||||
Each module gets a unique `name:modprobe.foo`, and optional`:ID`. The
|
||||
Each module is named `modprobe.foo`, with an optional `:ID`. The
|
||||
runlevel can be changed per file using:
|
||||
|
||||
set runlevel 2345
|
||||
|
||||
+5
-1
@@ -15,7 +15,11 @@ done slightly differently and on systems with udev you might want to add
|
||||
the following one-shot task early in your `/etc/finit.conf`:
|
||||
|
||||
```conf
|
||||
run [S] udevadm settle --timeout=120 -- Waiting for udev
|
||||
run udevadm {
|
||||
description = "Waiting for udev"
|
||||
runlevel = "S"
|
||||
command = "udevadm settle --timeout=120"
|
||||
}
|
||||
```
|
||||
|
||||
Finit has a built-in Getty for TTYs, but requires a working `/bin/login`
|
||||
|
||||
+36
-13
@@ -13,20 +13,37 @@ more of a policy for the user to define. Normally only runlevels 1-6
|
||||
are used, and even more commonly, only the default runlevel is used.
|
||||
|
||||
To specify an allowed set of runlevels for a `service`, `run` command,
|
||||
`task`, or `tty`, add `[NNN]` to your `/etc/finit.conf`, like this:
|
||||
`task`, or `tty`, set `runlevel` in your `/etc/finit.conf`, like this:
|
||||
|
||||
```
|
||||
service [S12345] syslogd -n -x -- System log daemon
|
||||
run [S] /etc/init.d/acpid start -- Starting ACPI Daemon
|
||||
task [S] /etc/init.d/kbd start -- Preparing console
|
||||
service [S12345] <pid/syslogd> klogd -n -x -- Kernel log daemon
|
||||
service syslogd {
|
||||
description = "System log daemon"
|
||||
runlevel = "S12345"
|
||||
command = "syslogd -n -x"
|
||||
}
|
||||
run acpid {
|
||||
description = "Starting ACPI Daemon"
|
||||
runlevel = "S"
|
||||
command = "/etc/init.d/acpid start"
|
||||
}
|
||||
task kbd {
|
||||
description = "Preparing console"
|
||||
runlevel = "S"
|
||||
command = "/etc/init.d/kbd start"
|
||||
}
|
||||
service klogd {
|
||||
description = "Kernel log daemon"
|
||||
runlevel = "S12345"
|
||||
conditions = { "pid/syslogd" }
|
||||
command = "klogd -n -x"
|
||||
}
|
||||
|
||||
tty [12345] /dev/tty1
|
||||
tty [2] /dev/tty2
|
||||
tty [2] /dev/tty3
|
||||
tty [2] /dev/tty4
|
||||
tty [2] /dev/tty5
|
||||
tty [2] /dev/tty6
|
||||
tty tty1 { runlevel = "12345" device = "/dev/tty1" }
|
||||
tty tty2 { runlevel = "2" device = "/dev/tty2" }
|
||||
tty tty3 { runlevel = "2" device = "/dev/tty3" }
|
||||
tty tty4 { runlevel = "2" device = "/dev/tty4" }
|
||||
tty tty5 { runlevel = "2" device = "/dev/tty5" }
|
||||
tty tty6 { runlevel = "2" device = "/dev/tty6" }
|
||||
```
|
||||
|
||||
In this example syslogd is first started, in parallel, and then acpid is
|
||||
@@ -46,8 +63,14 @@ are also removed when they have completed, `initctl show` will not list
|
||||
them.
|
||||
|
||||
```
|
||||
task [S] echo "foo" | cat >/tmp/bar
|
||||
run [S] echo "$HOME" >/tmp/secret
|
||||
task foo {
|
||||
runlevel = "S"
|
||||
command = "echo \"foo\" | cat >/tmp/bar"
|
||||
}
|
||||
run secret {
|
||||
runlevel = "S"
|
||||
command = "echo \"$HOME\" >/tmp/secret"
|
||||
}
|
||||
```
|
||||
|
||||
Switching between runlevels can be done by calling init with a single
|
||||
|
||||
+55
-11
@@ -51,27 +51,52 @@ Configuration file `/etc/finit.conf` in the initramfs:
|
||||
# /etc/finit.conf in initramfs
|
||||
|
||||
# Mount the real root filesystem
|
||||
run [S] name:mount-root /bin/mount /dev/sda1 /mnt/root -- Mounting root filesystem
|
||||
run mount-root {
|
||||
description = "Mounting root filesystem"
|
||||
runlevel = "S"
|
||||
command = "/bin/mount /dev/sda1 /mnt/root"
|
||||
}
|
||||
|
||||
# Switch to real root after mount completes
|
||||
run [S] name:switch-root /sbin/initctl switch-root /mnt/root -- Switching to real root
|
||||
run switch-root {
|
||||
description = "Switching to real root"
|
||||
runlevel = "S"
|
||||
command = "/sbin/initctl switch-root /mnt/root"
|
||||
}
|
||||
```
|
||||
|
||||
For more complex setups (LUKS, LVM, etc.):
|
||||
|
||||
```
|
||||
# Unlock LUKS volume
|
||||
# The tty:@console stanza is required so cryptsetup can prompt for a passphrase
|
||||
run [S] name:cryptsetup tty:@console /sbin/cryptsetup open /dev/sda2 cryptroot -- Unlocking encrypted root
|
||||
# The tty setting is required so cryptsetup can prompt for a passphrase
|
||||
run cryptsetup {
|
||||
description = "Unlocking encrypted root"
|
||||
runlevel = "S"
|
||||
tty = "@console"
|
||||
command = "/sbin/cryptsetup open /dev/sda2 cryptroot"
|
||||
}
|
||||
|
||||
# Activate LVM
|
||||
run [S] name:lvm /sbin/lvm vgchange -ay -- Activating LVM volumes
|
||||
run lvm {
|
||||
description = "Activating LVM volumes"
|
||||
runlevel = "S"
|
||||
command = "/sbin/lvm vgchange -ay"
|
||||
}
|
||||
|
||||
# Mount root
|
||||
run [S] name:mount-root /bin/mount /dev/vg0/root /mnt/root -- Mounting root
|
||||
run mount-root {
|
||||
description = "Mounting root"
|
||||
runlevel = "S"
|
||||
command = "/bin/mount /dev/vg0/root /mnt/root"
|
||||
}
|
||||
|
||||
# Switch root
|
||||
run [S] name:switch-root /sbin/initctl switch-root /mnt/root -- Switching to real root
|
||||
run switch-root {
|
||||
description = "Switching to real root"
|
||||
runlevel = "S"
|
||||
command = "/sbin/initctl switch-root /mnt/root"
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
@@ -85,15 +110,34 @@ difficult in runlevel S, you can perform the switch-root in runlevel 1:
|
||||
# /etc/finit.conf in initramfs
|
||||
|
||||
# Start mdevd for device handling
|
||||
service [S] name:mdevd notify:s6 /sbin/mdevd -D %n -- Device event daemon
|
||||
run [S] name:coldplug <service/mdevd/ready> /sbin/mdevd-coldplug -- Coldplug devices
|
||||
service mdevd {
|
||||
description = "Device event daemon"
|
||||
runlevel = "S"
|
||||
notify = "s6"
|
||||
command = "/sbin/mdevd -D %n"
|
||||
}
|
||||
run coldplug {
|
||||
description = "Coldplug devices"
|
||||
runlevel = "S"
|
||||
conditions = { "service/mdevd/ready" }
|
||||
command = "/sbin/mdevd-coldplug"
|
||||
}
|
||||
|
||||
# Mount the real root filesystem (after devices are ready)
|
||||
run [S] name:mount-root <run/coldplug/success> /bin/mount /dev/sda1 /mnt/root -- Mounting root
|
||||
run mount-root {
|
||||
description = "Mounting root"
|
||||
runlevel = "S"
|
||||
conditions = { "run/coldplug/success" }
|
||||
command = "/bin/mount /dev/sda1 /mnt/root"
|
||||
}
|
||||
|
||||
# Transition to runlevel 1 after all S tasks complete
|
||||
# The switch-root runs cleanly in runlevel 1
|
||||
run [1] name:switch-root /sbin/initctl switch-root /mnt/root -- Switching to real root
|
||||
run switch-root {
|
||||
description = "Switching to real root"
|
||||
runlevel = "1"
|
||||
command = "/sbin/initctl switch-root /mnt/root"
|
||||
}
|
||||
```
|
||||
|
||||
This approach separates the initramfs setup (runlevel S) from the
|
||||
|
||||
Reference in New Issue
Block a user