mirror of
https://github.com/troglobit/finit.git
synced 2026-10-13 10:14:47 +00:00
Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
54701422a5 | ||
|
|
9d463e3823 | ||
|
|
56e558c960 | ||
|
|
dfaf351da1 | ||
|
|
a8433fcb7f | ||
|
|
2daa953bee | ||
|
|
3e3e9aadf5 | ||
|
|
dc873c6548 | ||
|
|
29bd7a504e | ||
|
|
a0685219cf | ||
|
|
13b107b7b1 | ||
|
|
409d68d05b | ||
|
|
ab62b5282b | ||
|
|
d02d65feeb | ||
|
|
9a0dea6aef | ||
|
|
7481505b1a | ||
|
|
8251f1a422 | ||
|
|
e269176a79 | ||
|
|
612f5a9385 | ||
|
|
4a2381eb6f | ||
|
|
0cae7d44dd | ||
|
|
340cae4afd | ||
|
|
6a89e60fc8 | ||
|
|
840d612fc2 | ||
|
|
60c676ab2d | ||
|
|
deada0fa89 | ||
|
|
7b501f255b | ||
|
|
052136cb99 | ||
|
|
742b8b72cc | ||
|
|
c37037c015 | ||
|
|
c32b5a749a | ||
|
|
7701718d7b | ||
|
|
eb4eca9607 | ||
|
|
cab94b81e8 | ||
|
|
5913217808 | ||
|
|
b49f55ab3d | ||
|
|
bf4a584e2e | ||
|
|
90a4df8d12 | ||
|
|
146bf55122 | ||
|
|
c1ed373398 | ||
|
|
5998342b3e | ||
|
|
9dc7b8a6b0 | ||
|
|
c221823654 | ||
|
|
248f7d3110 | ||
|
|
fe90ba5781 | ||
|
|
71c87734b7 | ||
|
|
cd060e8af3 | ||
|
|
33a7f123d7 | ||
|
|
d15e28ea6b | ||
|
|
836bfff08b | ||
|
|
59152b557c | ||
|
|
293b0ffa79 | ||
|
|
d5d9cd5645 | ||
|
|
2f281665af | ||
|
|
b00e7394f8 | ||
|
|
d5a5fffa52 | ||
|
|
4d24c34b28 | ||
|
|
355265651e | ||
|
|
41093df2a9 | ||
|
|
0a816d1fa4 | ||
|
|
3bfc0f0fca | ||
|
|
0aa6ee895c | ||
|
|
b1526fb2d6 | ||
|
|
b2624ac160 | ||
|
|
2c340f83ce | ||
|
|
337ee003bb | ||
|
|
791df0c986 | ||
|
|
f29e92be21 | ||
|
|
379a63fce4 | ||
|
|
b1f9a11809 | ||
|
|
2d9c63e48e | ||
|
|
d66455496a | ||
|
|
77cf72cb40 | ||
|
|
6cc587068b | ||
|
|
cc96e8908a | ||
|
|
adb25d52cd | ||
|
|
7d09567ec8 | ||
|
|
9130af1c77 | ||
|
|
cbea83b369 | ||
|
|
42cd8d284b | ||
|
|
72ebc92622 | ||
|
|
06adecaaea | ||
|
|
efc0592961 | ||
|
|
ed88469276 | ||
|
|
cbf96a1de0 | ||
|
|
cc979f27f1 |
@@ -28,7 +28,7 @@ jobs:
|
||||
run: |
|
||||
sudo apt-get -y update
|
||||
sudo apt-get -y install pkg-config tree jq libuev-dev libite-dev
|
||||
- uses: actions/checkout@v3
|
||||
- uses: actions/checkout@v4
|
||||
- name: Static Finit
|
||||
run: |
|
||||
./autogen.sh
|
||||
@@ -61,7 +61,7 @@ jobs:
|
||||
run: |
|
||||
make check || (cat test/test-suite.log; false)
|
||||
- name: Upload Test Results
|
||||
uses: actions/upload-artifact@v3
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: finit-test-${{ matrix.compiler }}
|
||||
path: test/*.log
|
||||
|
||||
@@ -15,22 +15,39 @@ jobs:
|
||||
coverity:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
- uses: actions/cache@v3
|
||||
id: coverity-toolchain-cache
|
||||
with:
|
||||
path: cov-analysis-linux64
|
||||
key: ${{ runner.os }}-coverity
|
||||
- name: Download Coverity Scan
|
||||
if: steps.coverity-toolchain-cache.outputs.cache-hit != 'true'
|
||||
- uses: actions/checkout@v4
|
||||
- name: Fetch latest Coverity Scan MD5
|
||||
id: var
|
||||
env:
|
||||
TOKEN: ${{ secrets.COVERITY_SCAN_TOKEN }}
|
||||
run: |
|
||||
wget -q https://scan.coverity.com/download/cxx/linux64 \
|
||||
--post-data "token=$TOKEN&project=${COVERITY_PROJ}" \
|
||||
-O cov-analysis-linux64.tar.gz
|
||||
mkdir cov-analysis-linux64
|
||||
tar xzf cov-analysis-linux64.tar.gz --strip 1 -C cov-analysis-linux64
|
||||
wget -q https://scan.coverity.com/download/cxx/linux64 \
|
||||
--post-data "token=$TOKEN&project=${COVERITY_PROJ}&md5=1" \
|
||||
-O coverity-latest.tar.gz.md5
|
||||
echo "md5=$(cat coverity-latest.tar.gz.md5)" | tee -a $GITHUB_OUTPUT
|
||||
- uses: actions/cache@v4
|
||||
id: cache
|
||||
with:
|
||||
path: coverity-latest.tar.gz
|
||||
key: ${{ runner.os }}-coverity-${{ steps.var.outputs.md5 }}
|
||||
restore-keys: |
|
||||
${{ runner.os }}-coverity-${{ steps.var.outputs.md5 }}
|
||||
${{ runner.os }}-coverity-
|
||||
${{ runner.os }}-coverity
|
||||
- name: Download Coverity Scan
|
||||
env:
|
||||
TOKEN: ${{ secrets.COVERITY_SCAN_TOKEN }}
|
||||
run: |
|
||||
if [ ! -f coverity-latest.tar.gz ]; then
|
||||
wget -q https://scan.coverity.com/download/cxx/linux64 \
|
||||
--post-data "token=$TOKEN&project=${COVERITY_PROJ}" \
|
||||
-O coverity-latest.tar.gz
|
||||
else
|
||||
echo "Latest Coverity Scan available from cache :-)"
|
||||
md5sum coverity-latest.tar.gz
|
||||
fi
|
||||
mkdir coverity
|
||||
tar xzf coverity-latest.tar.gz --strip 1 -C coverity
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
sudo apt-get -y update
|
||||
@@ -42,13 +59,15 @@ jobs:
|
||||
(cd libuev-2.4.0 && ./configure --prefix=/usr && make && sudo make install-strip)
|
||||
(cd libite-2.5.2 && ./configure --prefix=/usr && make && sudo make install-strip)
|
||||
sudo ldconfig
|
||||
- name: Build
|
||||
- name: Configure
|
||||
run: |
|
||||
./autogen.sh
|
||||
./configure --prefix= --enable-x11-common-plugin --with-watchdog --with-keventd
|
||||
export PATH=`pwd`/cov-analysis-linux64/bin:$PATH
|
||||
- name: Build
|
||||
run: |
|
||||
export PATH=`pwd`/coverity/bin:$PATH
|
||||
cov-build --dir cov-int make
|
||||
- name: Submit result to Coverity Scan
|
||||
- name: Submit results to Coverity Scan
|
||||
env:
|
||||
TOKEN: ${{ secrets.COVERITY_SCAN_TOKEN }}
|
||||
run: |
|
||||
@@ -61,3 +80,8 @@ jobs:
|
||||
--form version=trunk \
|
||||
--form description="${PROJECT_NAME} $(git rev-parse HEAD)" \
|
||||
https://scan.coverity.com/builds?project=${COVERITY_PROJ}
|
||||
- name: Upload build.log
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: coverity-build.log
|
||||
path: cov-int/build-log.txt
|
||||
|
||||
@@ -13,7 +13,7 @@ jobs:
|
||||
env:
|
||||
MAKEFLAGS: -j3
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
- uses: actions/checkout@v4
|
||||
- name: Installing dependencies ...
|
||||
run: |
|
||||
sudo apt-get -y update
|
||||
|
||||
@@ -13,7 +13,7 @@ jobs:
|
||||
outputs:
|
||||
run: ${{ steps.check.outputs.run }}
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
- uses: actions/checkout@v4
|
||||
- name: Check for any commits since last week
|
||||
id: schedule
|
||||
run: |
|
||||
@@ -25,14 +25,14 @@ jobs:
|
||||
fi
|
||||
distcheck:
|
||||
needs: schedule
|
||||
if: ${{ needs.schedule.outputs.run }}
|
||||
if: ${{ needs.schedule.outputs.run == 'true' }}
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
sudo apt-get -y update
|
||||
sudo apt-get -y install pkg-config jq libuev-dev libite-dev
|
||||
- uses: actions/checkout@v3
|
||||
- uses: actions/checkout@v4
|
||||
- name: Base run
|
||||
run: |
|
||||
./autogen.sh
|
||||
|
||||
@@ -14,6 +14,7 @@ GTAGS
|
||||
/autom4te.cache
|
||||
/aclocal.m4
|
||||
/ar-lib
|
||||
/backup/
|
||||
/compile
|
||||
/config.cache
|
||||
/config.h
|
||||
@@ -36,6 +37,9 @@ GTAGS
|
||||
/test-driver
|
||||
/test-suite.log
|
||||
|
||||
# Misc
|
||||
/.gdb_history
|
||||
|
||||
# TroglOS build system
|
||||
/.config
|
||||
/.stamp
|
||||
|
||||
+74
-1
@@ -4,6 +4,77 @@ Change Log
|
||||
All relevant changes are documented in this file.
|
||||
|
||||
|
||||
[4.8][] - 2024-10-13
|
||||
--------------------
|
||||
|
||||
### Changes
|
||||
- Avoid remounting already mounted `/run` and `/tmp` directories. This
|
||||
extends the existing support for detecting mounted directories to
|
||||
include complex mount hierarchies are in use, overlayfs and tmpfs
|
||||
mounts. Feature by Mathias Thore, Atlas Copco
|
||||
- getty: trigger /etc/issue compat mode for Alpine Linux
|
||||
- tmpfiles.d: skip `x11.conf` unless X11 common plugin is enabled
|
||||
- tmpfiles.d: ignore x/X command, nos support for cleanup at runtime
|
||||
- Drop debug mode `-D` from `udevd` in `hotplug.conf.in`, allow the
|
||||
user to set this in `/etc/default/udevd` instead
|
||||
- Certain initctl APIs at bootstrap are not supported, update warning
|
||||
log to include command (number) for troubleshooting, issue #398
|
||||
- Add support for hwrng to urandom plugin and check for empty seed
|
||||
- Add `runparts -b` (batch mode) support, disables escape sequences
|
||||
- New configure `--without-rc-local`, disables `/etc/rc.local` support
|
||||
- New configure `--disable-cgroup` option, disables cgroup v2 detection
|
||||
- `initctl show template@foo.conf` now shows how an enabled template
|
||||
service has been evaluated by Finit, issue #411
|
||||
- Extend `initctl` timeout connecting and waiting for Finit reply. The
|
||||
previous 2 + 2 second poll timeout has proved to be too short on more
|
||||
complex systems. Now a 15 + 15 second timeout is applied which should
|
||||
be more resistant to temporary overload scenarios, issue #407
|
||||
|
||||
### Fixes
|
||||
- Fix #397: system shutdown/reboot can block on console input if action
|
||||
is started remotely (ssh). Caused by legact TTY screen size probing,
|
||||
removed from both bootstrap and shutdown/reboot
|
||||
- Fix #400: both `HOOK_MOUNT_ERROR` and `sulogin()` fail to trigger on
|
||||
either mount or `fsck` errors. Problem caused by unresolved status
|
||||
from pipe, calling `pclose()` without extracting exit status
|
||||
- Fix #402: `initctl touch` does not respect `-n` (no error) flag
|
||||
- Fix #403: `initctl touch` does not support template services
|
||||
- Fix #404: possible undefined behavior when `--with-fstab=no` is set
|
||||
- Fix #405: `@console` getty does not work with `tty0 ttyS0`
|
||||
- Fix #409: prevent tmpfiles from following symlinks for `L+` and `R`,
|
||||
otherwise symlink targets would also be removed. Found and fixed by
|
||||
Mathias Thore and Ming Liu, Atlas Copco
|
||||
- Fix #414: Frr Zebra immediately restarts on `initctl stop zebra`.
|
||||
The fix likely works for all Frr/Quagga services due to the way they
|
||||
create and delete their pid file
|
||||
- Cosmetic issue with `[ OK ]` messages being printed out of order at
|
||||
shutdown/reboot. Caused by nested calls to `service_stop()`
|
||||
- Cosmetic issue with duplicate "Restoring RTC" message at bootstrap
|
||||
|
||||
|
||||
[4.7][] - 2024-01-07
|
||||
--------------------
|
||||
|
||||
### Changes
|
||||
- Silence "not available" messages for run/task/service with `nowarn`
|
||||
- Update docs, `cgroup.root` workaround for `SCHED_RR` tasks
|
||||
- Drop runlevels 0 and 6 from `keventd`, not needed at reboot/poweroff
|
||||
- Mount `/dev/shm` with mode 1777 (sticky bit)
|
||||
- Mount `/dev/mqueue` if available, inspiration from Alpine Linux
|
||||
- Update Alpine Linux installer and configuration files, tested on
|
||||
Alpine v3.19, some assembly still required
|
||||
|
||||
### Fixes
|
||||
- Fix confusing warning message when tmpfiles.d fails to install symlink
|
||||
- Fix tmpfiles.d legacy `/run/lock/subsys`, ordering
|
||||
- Add missing `/var/tmp` and `/var/lock -> /run/lock` (tmpfiles.d)
|
||||
- Fix #388: log redirection broken unless Finit runs in debug mode.
|
||||
Found and fixed by Ryan Rorison
|
||||
- Fix #389: must libc requires `libgen.h` for `basename()` function.
|
||||
Reported and worked around with new `basenm()` function by Stargirl
|
||||
- Fix #392: `service/foo/ready` condition reasserted on pidfile removal
|
||||
|
||||
|
||||
[4.6][] - 2023-11-13
|
||||
--------------------
|
||||
|
||||
@@ -1633,7 +1704,9 @@ Major bug fix release.
|
||||
|
||||
* Initial release
|
||||
|
||||
[UNRELEASED]: https://github.com/troglobit/finit/compare/4.6...HEAD
|
||||
[UNRELEASED]: https://github.com/troglobit/finit/compare/4.8...HEAD
|
||||
[4.8]: https://github.com/troglobit/finit/compare/4.7...4.8
|
||||
[4.7]: https://github.com/troglobit/finit/compare/4.6...4.7
|
||||
[4.6]: https://github.com/troglobit/finit/compare/4.5...4.6
|
||||
[4.5]: https://github.com/troglobit/finit/compare/4.4...4.5
|
||||
[4.4]: https://github.com/troglobit/finit/compare/4.3...4.4
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -22,11 +22,10 @@ Introduction
|
||||
------------
|
||||
|
||||
Fast init for Linux systems. Reverse engineered from the [EeePC
|
||||
fastinit][] over ten years ago by [Claudio Matsuoka][] — "gaps filled
|
||||
with frog DNA …"
|
||||
fastinit][] by [Claudio Matsuoka][] — "gaps filled with frog DNA …"
|
||||
|
||||

|
||||
*Figure 1: Screenshot showing Finit booting [Alpine Linux](https://www.alpinelinux.org/).*
|
||||

|
||||
*Figure 1: Screenshot of Finit booting [Alpine Linux (HowTo)](https://github.com/troglobit/finit/tree/master/contrib/alpine).*
|
||||
|
||||
Features include:
|
||||
|
||||
@@ -65,7 +64,9 @@ distributions:
|
||||
> **Note:** support for various Linux distributions does not mean Finit
|
||||
> installs easily on all architectures. The bundled install scripts are
|
||||
> examples for standard installations, tested on amd64 (x86_64) systems.
|
||||
> Custom setups, for embedded systems, can be found in [myLinux][].
|
||||
> Custom setups, e.g., for embedded systems, can be found in any of the
|
||||
> following [Buildroot][] based examples: [myLinux][], [Infix][], or the
|
||||
> plain [br2-finit-demo](https://github.com/troglobit/br2-finit-demo).
|
||||
|
||||
|
||||
Example
|
||||
@@ -404,8 +405,7 @@ The event loop is the whole thing which Finit is built around, except
|
||||
for runlevel S, which remains a slow procession through a lot of set up,
|
||||
with a few hooks and blocking call outs to external scripts.
|
||||
|
||||
However, not all `initctl` commands are prohibited, supported commands:
|
||||
are:
|
||||
However, not all `initctl` commands are prohibited. Supported commands:
|
||||
|
||||
- `inictl cond`: only operate of files in `/run/finit/cond`
|
||||
- `initctl enable/disable`: enabled run/task/service is activated on
|
||||
@@ -705,6 +705,8 @@ and proposed extensions.
|
||||
[EeePC fastinit]: https://web.archive.org/web/20071208212450/http://wiki.eeeuser.com/boot_process:the_boot_process
|
||||
[Claudio Matsuoka]: https://github.com/cmatsuoka
|
||||
[Joachim Wiberg]: https://troglobit.com
|
||||
[Buildroot]: https://buildroot.org
|
||||
[Infix]: https://kernelkit.github.io
|
||||
[finit.conf(5)]: https://man.troglobit.com/man5/finit.conf.5.html
|
||||
[License]: https://en.wikipedia.org/wiki/MIT_License
|
||||
[License Badge]: https://img.shields.io/badge/License-MIT-teal.svg
|
||||
|
||||
+25
-8
@@ -1,4 +1,4 @@
|
||||
AC_INIT([Finit], [4.6], [https://github.com/troglobit/finit/issues],
|
||||
AC_INIT([Finit], [4.8], [https://github.com/troglobit/finit/issues],
|
||||
[finit], [https://troglobit.com/projects/finit/])
|
||||
AC_CONFIG_AUX_DIR(aux)
|
||||
AM_INIT_AUTOMAKE([1.11 foreign dist-xz subdir-objects])
|
||||
@@ -67,10 +67,18 @@ AC_ARG_ENABLE(fsckfix,
|
||||
AS_HELP_STRING([--enable-fsckfix], [Run fsck fix mode (options: -yf) on filesystems listed in /etc/fstab]),,[
|
||||
enable_fsckfix=no])
|
||||
|
||||
AC_ARG_ENABLE(cgroup,
|
||||
AS_HELP_STRING([--disable-cgroup], [Disable cgroup v2 support, default: autodetect from /sys/fs/cgroup]),,[
|
||||
enable_cgroup=yes])
|
||||
|
||||
AC_ARG_ENABLE(redirect,
|
||||
AS_HELP_STRING([--disable-redirect], [Disable redirection of service output to /dev/null]),,[
|
||||
enable_redirect=yes])
|
||||
|
||||
AC_ARG_ENABLE(kernel_logging,
|
||||
AS_HELP_STRING([--disable-kernel-logging], [Disable kernel logging to console (use 'quiet' instead!]),,[
|
||||
enable_kernel_logging=yes])
|
||||
|
||||
AC_ARG_ENABLE(logrotate,
|
||||
AS_HELP_STRING([--disable-logrotate], [Disable built-in rotation of /var/log/wtmp]),,[
|
||||
enable_logrotate=yes])
|
||||
@@ -181,6 +189,12 @@ AS_IF([test "x$enable_auto_reload" = "xyes"], [
|
||||
AS_IF([test "x$enable_kernel_cmdline" = "xyes"], [
|
||||
AC_DEFINE(KERNEL_CMDLINE, 1, [Dumpster diving after init args from /proc/cmdline])])
|
||||
|
||||
AS_IF([test "x$enable_kernel_logging" = "xyes"], [
|
||||
AC_DEFINE(KERNEL_LOGGING, 1, [Keep kernel warn/err logs to console])])
|
||||
|
||||
AS_IF([test "x$enable_cgroup" = "xyes"], [
|
||||
AC_DEFINE(CGROUP2_ENABLED, 1, [Autodetect cgroup v2 support from /sys/fs/cgroup])])
|
||||
|
||||
AS_IF([test "x$enable_fastboot" = "xyes"], [
|
||||
AC_DEFINE(FAST_BOOT, 1, [Skip fsck check on filesystems listed in /etc/fstab])])
|
||||
|
||||
@@ -227,10 +241,9 @@ AC_DEFINE_UNQUOTED(FINIT_RCSD, "$rcsd_path", [Finit rcS.d/, default /etc/finit.d
|
||||
AC_SUBST(FINIT_RCSD, "$rcsd_path")
|
||||
|
||||
AS_IF([test "x$with_rc_local" != "xno"], [
|
||||
AS_IF([test "x$rclocal" = "xyes"], [
|
||||
rclocal=$sysconfdir/rc.local])])
|
||||
AC_EXPAND_DIR(rclocal_path, "$rclocal")
|
||||
AC_DEFINE_UNQUOTED(FINIT_RC_LOCAL, "$rclocal_path", [Compat SysV /etc/rc.local file to run last at boot.])
|
||||
AS_IF([test "x$rclocal" = "xyes"], [rclocal=$sysconfdir/rc.local])
|
||||
AC_EXPAND_DIR(rclocal_path, "$rclocal")
|
||||
AC_DEFINE_UNQUOTED(FINIT_RC_LOCAL, "$rclocal_path", [Compat SysV /etc/rc.local file to run last at boot.])])
|
||||
|
||||
AS_IF([test "x$with_sysconfig" != "xno"], [
|
||||
AS_IF([test "x$sysconfig" != "xdefault"], [
|
||||
@@ -355,15 +368,16 @@ cat <<EOF
|
||||
|
||||
------------------ Summary ------------------
|
||||
$PACKAGE_NAME version $PACKAGE_VERSION
|
||||
Prefix................: $prefix
|
||||
Exec prefix...........: $eprefix
|
||||
Prefix................: $(eval echo $prefix)
|
||||
Exec prefix...........: $(eval echo $exec_prefix)
|
||||
Libdir................: $(eval echo $libdir)
|
||||
Sysconfdir............: `eval echo $sysconfdir`
|
||||
Localstatedir.........: `eval echo $localstatedir`
|
||||
Default fstab.........: `eval echo $fstab`
|
||||
Finit config file.....: $conf_path
|
||||
Finit config.d path...: $rcsd_path
|
||||
Finit plugin path.....: $plugin_path
|
||||
Compat rc.local path..: $rclocal_path
|
||||
Compat rc.local path..: `eval echo $rclocal`
|
||||
System environment....: ${sysconfig_path:-${sysconfig}}
|
||||
Random seed path......: $random_path
|
||||
C Compiler............: $CC $CFLAGS $CPPFLAGS $LDFLAGS $LIBS
|
||||
@@ -382,6 +396,9 @@ Optional features:
|
||||
Built-in sulogin......: $with_sulogin $sulogin
|
||||
Built-in watchdogd....: $with_watchdog $watchdog
|
||||
Built-in logrotate....: $enable_logrotate
|
||||
Use cgroup v2.........: $enable_cgroup
|
||||
Parse kernel cmdline..: $enable_kernel_cmdline
|
||||
Keep kernel logging...: $enable_kernel_logging
|
||||
Skip fsck check.......: $enable_fastboot
|
||||
Run fsck fix mode.....: $enable_fsckfix
|
||||
Redirect output.......: $enable_redirect
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
HowTo: Finit on Alpine Linux 3.4-3.6
|
||||
====================================
|
||||
HowTo: Finit on Alpine Linux 3.4...3.19
|
||||
=======================================
|
||||
|
||||
> **Blog** https://troglobit.com/post/2021-02-12-alpine-linux-with-finit/
|
||||
|
||||
HowTo use Finit to boot an [Alpine Linux][] system. It is assumed that
|
||||
the user has already installed make, a compiler, C library header files,
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
SUBDIRS = available
|
||||
docsdir := @docdir@/contrib/alpine/finit.d
|
||||
d_LINKS = acpid.conf crond.conf dropbear.conf getty.conf \
|
||||
keymap.conf modules.conf ntpd.conf \
|
||||
klogd.conf syslogd.conf
|
||||
keymap.conf modules.conf ntpd.conf syslogd.conf
|
||||
|
||||
install-exec-hook:
|
||||
@$(MKDIR_P) $(DESTDIR)$(docsdir)/available
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
docsdir := @docdir@/contrib/alpine/finit.d/available
|
||||
docs_DATA = acpid.conf crond.conf dropbear.conf getty.conf keymap.conf \
|
||||
lxdm.conf modules.conf ntpd.conf syslog.conf watchdog.conf
|
||||
lxdm.conf modules.conf ntpd.conf syslogd.conf watchdog.conf
|
||||
EXTRA_DIST = $(docs_DATA)
|
||||
|
||||
@@ -4,4 +4,4 @@
|
||||
#module evdev
|
||||
#module mousedev
|
||||
#module 8139cp
|
||||
module softdog
|
||||
#module softdog
|
||||
|
||||
+35
-29
@@ -1,45 +1,53 @@
|
||||
#!/bin/sh
|
||||
|
||||
if [ "x`id -u`" != "x0" ]; then
|
||||
echo
|
||||
echo "*** This script must run as root"
|
||||
echo
|
||||
if [ "$(id -u)" != "0" ]; then
|
||||
printf "\n\e[1m*** This script must run as root\e[0m\n\n"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# shellcheck disable=SC3037,SC3045,SC2154
|
||||
yorn()
|
||||
{
|
||||
printf "\e[1m> %s (y/N)?\e[0m " "$*"
|
||||
read -rn1 yorn
|
||||
echo
|
||||
|
||||
if [ "$yorn" = "y" ] || [ "$yorn" = "Y" ]; then
|
||||
return 0
|
||||
fi
|
||||
|
||||
return 1
|
||||
}
|
||||
|
||||
# Adjust base directory
|
||||
grep -q alpine Makefile 2>/dev/null
|
||||
if [ $? -eq 0 ]; then
|
||||
if grep -q contrib/alpine Makefile 2>/dev/null; then
|
||||
cd ../..
|
||||
elif [ ! -e configure.ac ]; then
|
||||
echo "*** Please run this script from the Finit base directory."
|
||||
fi
|
||||
|
||||
if [ ! -e configure.ac ]; then
|
||||
printf "\n\e[1m*** Please run this script from the Finit base directory.\e[0m\n"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
echo
|
||||
echo "*** Install Finit on Alpine Linux"
|
||||
echo "========================================================================"
|
||||
echo "/sbin/finit - PID 1"
|
||||
echo "/lib/finit/plugins/* - All enabled Finit plugins"
|
||||
echo "/etc/finit.conf - Finit configuration file"
|
||||
echo "/etc/finit.d/ - Finit services"
|
||||
echo
|
||||
read -p "Do you want to continue (y/N)? " yorn
|
||||
printf "\n\e[1mInstall Finit on Alpine Linux\n"
|
||||
printf "========================================================================\e[0m\n"
|
||||
printf "/sbin/finit - PID 1\n"
|
||||
printf "/lib/finit/plugins/* - All enabled Finit plugins\n"
|
||||
printf "/etc/finit.conf - Finit configuration file\n"
|
||||
printf "/etc/finit.d/ - Finit services\n"
|
||||
|
||||
if [ "x$yorn" = "xy" -o "x$yorn" = "xY" ]; then
|
||||
echo
|
||||
echo "*** Installing Finit files ..."
|
||||
if yorn "Do you want to continue"; then
|
||||
printf "\n\e[1m*** Installing Finit files ...\e[0m\n"
|
||||
make install
|
||||
cd /usr/share/doc/finit/contrib/alpine
|
||||
cd /usr/share/doc/finit/contrib/alpine || exit 1
|
||||
for file in finit.conf rc.local; do
|
||||
install -vbD $file /etc/$file
|
||||
done
|
||||
cp -va finit.d /etc/
|
||||
|
||||
read -p "*** Install Finit as the system default Init (y/N)? " yorn
|
||||
if [ "x$yorn" = "xy" -o "x$yorn" = "xY" ]; then
|
||||
echo "*** Updating /sbin/init symlink --> finit ..."
|
||||
cd /sbin
|
||||
if yorn "Install Finit as the system default Init"; then
|
||||
printf "\e[1m*** Updating /sbin/init symlink --> finit ...\e[0m\n"
|
||||
cd /sbin || exit 1
|
||||
rm init
|
||||
ln -s finit init
|
||||
|
||||
@@ -48,10 +56,8 @@ if [ "x$yorn" = "xy" -o "x$yorn" = "xY" ]; then
|
||||
ln -s reboot shutdown
|
||||
ln -s reboot suspend
|
||||
fi
|
||||
echo "*** Done"
|
||||
printf "\n\e[1m*** Done\e[0m\n"
|
||||
echo
|
||||
else
|
||||
echo
|
||||
echo "*** Aborting install."
|
||||
echo
|
||||
printf "\n\e[1m*** Aborting install.\e[0m\n\n"
|
||||
fi
|
||||
|
||||
+5
-1
@@ -459,7 +459,7 @@ Cgroups
|
||||
|
||||
There are three major cgroup configuration directives:
|
||||
|
||||
1. Global top-level group: init, system, user, or a custom group
|
||||
1. Global top-level group: `init`, `system`, `user`, or a custom group
|
||||
2. Selecting a top-level group for a set of run/task/services
|
||||
3. Per run/task/service limits
|
||||
|
||||
@@ -510,6 +510,10 @@ except for expanding the shorthand `mem.` to `memory.`, if the file is
|
||||
not available, either the cgroup controller is not available in your
|
||||
Linux kernel, or the name is misspelled.
|
||||
|
||||
A daemon using `SCHED_RR` currently need to run outside the default cgroups.
|
||||
|
||||
service [...] <...> cgroup.root /path/to/daemon arg -- Real-Time process
|
||||
|
||||
> Linux cgroups and details surrounding values are not explained in the
|
||||
> Finit documentation. The Linux admin-guide cover this well:
|
||||
> <https://www.kernel.org/doc/html/latest/admin-guide/cgroup-v2.html>
|
||||
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 20 KiB |
@@ -1,6 +1,6 @@
|
||||
/* Save and restore ALSA sound settings using alsactl
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Setup necessary system files for, e.g. UTMP (tracking logins)
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Setup and start system message bus, D-Bus
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+3
-4
@@ -1,6 +1,6 @@
|
||||
/* Coldplug modules using modalias magic
|
||||
*
|
||||
* Copyright (c) 2021-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2021-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -132,11 +132,10 @@ static FILE *maybe_fopen_alias(const char *file, const char *path)
|
||||
{
|
||||
const char *basename;
|
||||
|
||||
basename = rindex(path, '/');
|
||||
if (!basename)
|
||||
basename = basenm(path);
|
||||
if (!strcmp(basename, path))
|
||||
return NULL;
|
||||
|
||||
basename++;
|
||||
if (strcmp(file, basename))
|
||||
return NULL;
|
||||
|
||||
|
||||
+1
-1
@@ -2,7 +2,7 @@
|
||||
/* Netlink plugin for IFUP/IFDN and GW events
|
||||
*
|
||||
* Copyright (C) 2009-2011 Mårten Wikström <marten.wikstrom@keystream.se>
|
||||
* Copyright (C) 2009-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (C) 2009-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission to use, copy, modify, and/or distribute this software for any
|
||||
* purpose with or without fee is hereby granted, provided that the above
|
||||
|
||||
+15
-6
@@ -1,7 +1,7 @@
|
||||
/* Simple pidfile event monitor for the Finit condition engine
|
||||
*
|
||||
* Copyright (c) 2015-2016 Tobias Waldekranz <tobias@waldekranz.com>
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -52,7 +52,7 @@ static int pidfile_add_path(struct iwatch *iw, char *path)
|
||||
ptr = slash++;
|
||||
slash = strchr(ptr, '/');
|
||||
if (slash) {
|
||||
dbg("Path too deep, skipping.");
|
||||
dbg("Path too deep, skipping %s", path);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
@@ -66,6 +66,7 @@ static void pidfile_update_conds(char *dir, char *name, uint32_t mask)
|
||||
char cond[MAX_COND_LEN];
|
||||
char fn[PATH_MAX];
|
||||
svc_t *svc;
|
||||
char *nm;
|
||||
|
||||
paste(fn, sizeof(fn), dir, name);
|
||||
if (fnmatch("*\\.pid", fn, 0) && fnmatch("*/pid", fn, 0))
|
||||
@@ -79,9 +80,16 @@ static void pidfile_update_conds(char *dir, char *name, uint32_t mask)
|
||||
return;
|
||||
}
|
||||
|
||||
dbg("Found svc %s for %s with pid %d", svc_ident(svc, NULL, 0), fn, svc->pid);
|
||||
/* Service condistion to set/clear */
|
||||
mkcond(svc, cond, sizeof(cond));
|
||||
|
||||
nm = svc_ident(svc, NULL, 0);
|
||||
dbg("Found svc %s for %s with pid %d", nm, fn, svc->pid);
|
||||
if (svc_is_stopping(svc)) {
|
||||
dbg("Ignoring pidfile death rattles while service %s is %s", nm, svc_status(svc));
|
||||
goto sneaky_zebra;
|
||||
}
|
||||
|
||||
if (mask & (IN_CLOSE_WRITE | IN_ATTRIB | IN_MODIFY | IN_MOVED_TO)) {
|
||||
/*
|
||||
* only mark native services as started, the s6 and
|
||||
@@ -123,11 +131,12 @@ static void pidfile_update_conds(char *dir, char *name, uint32_t mask)
|
||||
if (svc->notify == SVC_NOTIFY_PID)
|
||||
cond_set(cond);
|
||||
if (svc->notify == SVC_NOTIFY_PID || svc->notify == SVC_NOTIFY_NONE)
|
||||
service_ready(svc);
|
||||
service_ready(svc, 1);
|
||||
} else if (mask & IN_DELETE) {
|
||||
sneaky_zebra:
|
||||
cond_clear(cond);
|
||||
if (svc->notify == SVC_NOTIFY_PID)
|
||||
service_ready(svc);
|
||||
service_ready(svc, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -242,7 +251,7 @@ static void pidfile_reconf(void *arg)
|
||||
continue;
|
||||
|
||||
if (svc->notify == SVC_NOTIFY_PID)
|
||||
service_ready(svc);
|
||||
service_ready(svc, 1);
|
||||
|
||||
mkcond(svc, cond, sizeof(cond));
|
||||
if (cond_get(cond) == COND_ON)
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Set kernel variables from /etc/sysctl.conf et al
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* Setup necessary files for resolvconf
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+3
-2
@@ -1,6 +1,6 @@
|
||||
/* Save and restore RTC using hwclock
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -180,7 +180,8 @@ static void rtc_restore(void *arg)
|
||||
rc = 2;
|
||||
}
|
||||
|
||||
print_desc(NULL, "Restoring system clock (UTC) from RTC");
|
||||
if (!rc)
|
||||
print_desc(NULL, "Restoring system clock (UTC) from RTC");
|
||||
tm.tm_isdst = -1; /* Use tzdata to figure it out, please. */
|
||||
tv.tv_sec = mktime(&tm);
|
||||
if (tv.tv_sec == (time_t)-1 || tv.tv_sec < rtc_date_fallback) {
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* System condition event monitor for the Finit condition engine
|
||||
*
|
||||
* Copyright (c) 2021-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2021-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
/* Optional TTY Watcher, used to catch new TTYs that are discovered, e.g., USB
|
||||
*
|
||||
* Copyright (c) 2013 Mattias Walström <lazzer@gmail.com>
|
||||
* Copyright (c) 2013-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2013-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+34
-10
@@ -1,6 +1,6 @@
|
||||
/* Setup and save random seed at boot/shutdown
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -42,11 +42,29 @@
|
||||
#define RANDOM_BYTES (32*1024)
|
||||
#endif
|
||||
|
||||
#ifdef RANDOMSEED
|
||||
static void fallback(FILE *fp)
|
||||
{
|
||||
struct timeval tv;
|
||||
int iter = 128;
|
||||
|
||||
gettimeofday(&tv, NULL);
|
||||
srandom(tv.tv_sec % 3600);
|
||||
while (iter--) {
|
||||
uint32_t i, prng = random();
|
||||
|
||||
for (i = 0; i < sizeof(prng); i++)
|
||||
fputc((prng >> (i * CHAR_BIT)) & UCHAR_MAX, fp);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
static void setup(void *arg)
|
||||
{
|
||||
#ifdef RANDOMSEED
|
||||
struct rand_pool_info *rpi;
|
||||
ssize_t len = 0;
|
||||
struct stat st;
|
||||
int rc = -1;
|
||||
int fd, err;
|
||||
|
||||
@@ -55,7 +73,7 @@ static void setup(void *arg)
|
||||
return;
|
||||
}
|
||||
|
||||
if (!fexist(RANDOMSEED)) {
|
||||
if (stat(RANDOMSEED, &st) || st.st_size < 512) {
|
||||
int ret = 1;
|
||||
mode_t prev;
|
||||
FILE *fp;
|
||||
@@ -64,16 +82,22 @@ static void setup(void *arg)
|
||||
prev = umask(077);
|
||||
fp = fopen(RANDOMSEED, "w");
|
||||
if (fp) {
|
||||
int iter = 128;
|
||||
struct timeval tv;
|
||||
const char *hwrng = "/dev/hwrng";
|
||||
FILE *hw;
|
||||
|
||||
gettimeofday(&tv, NULL);
|
||||
srandom(tv.tv_sec % 3600);
|
||||
while (iter--) {
|
||||
uint32_t i, prng = random();
|
||||
hw = fopen(hwrng, "r");
|
||||
if (hw) {
|
||||
char buf[512];
|
||||
size_t len;
|
||||
|
||||
for (i = 0; i < sizeof(prng); i++)
|
||||
fputc((prng >> (i * CHAR_BIT)) & UCHAR_MAX, fp);
|
||||
len = fread(buf, sizeof(buf[0]), sizeof(buf), hw);
|
||||
if (len == 0)
|
||||
fallback(fp);
|
||||
else
|
||||
len = fwrite(buf, sizeof(buf[0]), len, fp);
|
||||
fclose(hw);
|
||||
} else {
|
||||
fallback(fp);
|
||||
}
|
||||
ret = fclose(fp);
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* User-defined condition event monitor for the Finit condition engine
|
||||
*
|
||||
* Copyright (c) 2021-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2021-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* Console setup (for X)
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* External client API, using UNIX domain socket.
|
||||
*
|
||||
* Copyright (c) 2015-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2015-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -377,7 +377,9 @@ static void api_cb(uev_t *w, void *arg, int events)
|
||||
case INIT_CMD_POWEROFF:
|
||||
case INIT_CMD_SUSPEND:
|
||||
if (IS_RESERVED_RUNLEVEL(runlevel)) {
|
||||
warnx("Unsupported command in runlevel S and 6/0.");
|
||||
strterm(rq.data, sizeof(rq.data));
|
||||
warnx("Unsupported command (cmd: %d, data: %s) in runlevel S and 6/0.",
|
||||
rq.cmd, rq.data);
|
||||
goto leave;
|
||||
}
|
||||
default:
|
||||
|
||||
+6
-1
@@ -1,6 +1,6 @@
|
||||
/* Finit control group support functions
|
||||
*
|
||||
* Copyright (c) 2019-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2019-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -463,6 +463,11 @@ void cgroup_init(uev_ctx_t *ctx)
|
||||
FILE *fp;
|
||||
int fd;
|
||||
|
||||
#ifndef CGROUP2_ENABLED
|
||||
avail = 0;
|
||||
return;
|
||||
#endif
|
||||
|
||||
if (mount("none", FINIT_CGPATH, "cgroup2", opts, NULL)) {
|
||||
if (errno == ENOENT)
|
||||
logit(LOG_INFO, "Kernel does not support cgroups v2, disabling.");
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Finit control group support functions
|
||||
*
|
||||
* Copyright (c) 2019-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2019-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* New client tool, replaces old /dev/initctl API and telinit tool
|
||||
*
|
||||
* Copyright (c) 2019-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2019-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Cgroup utility functions for initctl
|
||||
*
|
||||
* Copyright (c) 2019-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2019-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+5
-3
@@ -1,6 +1,6 @@
|
||||
/* External client API, using UNIX domain socket.
|
||||
*
|
||||
* Copyright (c) 2015-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2015-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -29,6 +29,8 @@
|
||||
#include "client.h"
|
||||
#include "log.h"
|
||||
|
||||
#define REQUEST_TIMEOUT 15000
|
||||
|
||||
static int sd = -1;
|
||||
|
||||
int client_connect(void)
|
||||
@@ -85,7 +87,7 @@ int client_request(struct init_request *rq, ssize_t len)
|
||||
|
||||
pfd.fd = sd;
|
||||
pfd.events = POLLOUT;
|
||||
if (poll(&pfd, 1, 2000) <= 0) {
|
||||
if (poll(&pfd, 1, REQUEST_TIMEOUT) <= 0) {
|
||||
warn("Timed out waiting for Finit, errno %d", errno);
|
||||
return -1;
|
||||
}
|
||||
@@ -107,7 +109,7 @@ int client_request(struct init_request *rq, ssize_t len)
|
||||
|
||||
pfd.fd = sd;
|
||||
pfd.events = POLLIN | POLLERR | POLLHUP;
|
||||
if ((rc = poll(&pfd, 1, 2000)) <= 0) {
|
||||
if ((rc = poll(&pfd, 1, REQUEST_TIMEOUT)) <= 0) {
|
||||
if (rc) {
|
||||
if (errno == EINTR) /* shutdown/reboot */
|
||||
return -1;
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* External client API, using UNIX domain socket.
|
||||
*
|
||||
* Copyright (c) 2015-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2015-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+5
-1
@@ -35,6 +35,7 @@
|
||||
#include "cond.h"
|
||||
#include "pid.h"
|
||||
#include "service.h"
|
||||
#include "sm.h"
|
||||
|
||||
struct cond_boot {
|
||||
TAILQ_ENTRY(cond_boot) link;
|
||||
@@ -214,7 +215,10 @@ static int do_delete(const char *fpath, const struct stat *sb, int tflag, struct
|
||||
err(1, "Failed removing condition %s", fpath);
|
||||
|
||||
cond = ptr + strlen(COND_BASE) + 1;
|
||||
cond_update(cond);
|
||||
if (sm_is_in_teardown(&sm))
|
||||
cond_clear_noupdate(cond);
|
||||
else
|
||||
cond_update(cond);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
+7
-4
@@ -1,6 +1,6 @@
|
||||
/* Parser for /etc/finit.conf and /etc/finit.d/<SVC>.conf
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -348,8 +348,11 @@ static void parse_kernel_loglevel(void)
|
||||
*/
|
||||
void conf_parse_cmdline(int argc, char *argv[])
|
||||
{
|
||||
const char *ptr;
|
||||
|
||||
/* Set up defaults */
|
||||
fstab = strdup(FINIT_FSTAB);
|
||||
if ((ptr = FINIT_FSTAB))
|
||||
fstab = strdup(ptr);
|
||||
finit_conf = strdup(FINIT_CONF);
|
||||
finit_rcsd = strdup(FINIT_RCSD);
|
||||
path = getenv("PATH");
|
||||
@@ -1311,7 +1314,7 @@ int conf_reload(void)
|
||||
if (strncmp(path, FINIT_SYSPATH_, strlen(FINIT_SYSPATH_)) &&
|
||||
strncmp(path, FINIT_RUNPATH_, strlen(FINIT_RUNPATH_)))
|
||||
continue;
|
||||
if (strcmp(basename(path), basename(gl.gl_pathv[j])))
|
||||
if (strcmp(basenm(path), basenm(gl.gl_pathv[j])))
|
||||
continue;
|
||||
path = NULL; /* replacement later in list, skip this */
|
||||
break;
|
||||
@@ -1617,7 +1620,7 @@ int conf_init(uev_ctx_t *ctx)
|
||||
* Start kernel event daemon as soon as possible, if enabled
|
||||
*/
|
||||
if (whichp(FINIT_EXECPATH_ "/keventd"))
|
||||
conf_save_service(SVC_TYPE_SERVICE, "[S0123456789] cgroup.init notify:none "
|
||||
conf_save_service(SVC_TYPE_SERVICE, "[S12345789] cgroup.init notify:none "
|
||||
FINIT_EXECPATH_ "/keventd -- Finit kernel event daemon", "keventd.conf");
|
||||
|
||||
dbg("Allow plugins to register early runlevel 1 run/task/services ...");
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Parser for /etc/finit.conf and /etc/finit.d/<SVC>.conf
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Device node monitor for the Finit condition engine
|
||||
*
|
||||
* Copyright (c) 2022-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2022-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Device node monitor for the Finit condition engine
|
||||
*
|
||||
* Copyright (c) 2022-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2022-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+19
-18
@@ -1,7 +1,7 @@
|
||||
/* Functions for exec'ing processes
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -138,31 +138,32 @@ int run(char *cmd, char *log)
|
||||
|
||||
pid = fork();
|
||||
if (0 == pid) {
|
||||
int rc = EX_OSERR;
|
||||
char *pfx, buf[256];
|
||||
FILE *pp;
|
||||
int rc;
|
||||
|
||||
setsid();
|
||||
sig_unblock();
|
||||
if (!log) {
|
||||
do_redirect();
|
||||
execvp(args[0], args);
|
||||
} else {
|
||||
char *pfx = *log ? ": " : "";
|
||||
FILE *pp;
|
||||
|
||||
pp = popen(cmd, "r");
|
||||
if (pp) {
|
||||
char buf[256];
|
||||
|
||||
while (fgets(buf, sizeof(buf), pp)) {
|
||||
chomp(buf);
|
||||
logit(LOG_NOTICE, "%s%s%s", log, pfx, buf);
|
||||
}
|
||||
|
||||
rc = pclose(pp);
|
||||
}
|
||||
_exit(EX_OSERR);
|
||||
}
|
||||
|
||||
_exit(rc);
|
||||
pp = popen(cmd, "r");
|
||||
if (!pp)
|
||||
_exit(EX_OSERR);
|
||||
|
||||
pfx = *log ? ": " : "";
|
||||
while (fgets(buf, sizeof(buf), pp)) {
|
||||
chomp(buf);
|
||||
logit(LOG_NOTICE, "%s%s%s", log, pfx, buf);
|
||||
}
|
||||
|
||||
rc = pclose(pp);
|
||||
if (rc == -1)
|
||||
_exit(EX_OSERR);
|
||||
_exit(WEXITSTATUS(rc));
|
||||
} else if (-1 == pid) {
|
||||
err(1, "%s", !log ? args[0] : cmd);
|
||||
if (backup)
|
||||
|
||||
+25
-9
@@ -1,7 +1,7 @@
|
||||
/* Finit - Fast /sbin/init replacement w/ I/O, hook & service plugins
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -87,14 +87,22 @@ svc_t *wdog = NULL; /* No watchdog by default */
|
||||
*/
|
||||
static void banner(void)
|
||||
{
|
||||
#ifndef KERNEL_LOGGING
|
||||
/*
|
||||
* Silence kernel logs, assuming users have sysklogd or
|
||||
* similar enabled to start emptying /dev/kmsg, but for
|
||||
* our progress we want to own the console.
|
||||
* similar enabled to start emptying /dev/kmsg.
|
||||
*
|
||||
* Instead of using `configure --disable-kernel-logging`, we
|
||||
* recommend adjusting the kernel log level in the kernel's
|
||||
* menuconfig, or using sysctl kernel.printk, or setting the
|
||||
* desired log level, on the kernel cmdline, e.g. 'quiet'.
|
||||
*
|
||||
* By default KERNEL_LOGGING is enabled so you can see any
|
||||
* warnings/errors or higher on your system console.
|
||||
*/
|
||||
if (!debug && !kerndebug)
|
||||
klogctl(6, NULL, 0);
|
||||
|
||||
#endif
|
||||
/*
|
||||
* First level hooks, if you want to run here, you're
|
||||
* pretty much on your own. Nothing's up yet ...
|
||||
@@ -355,6 +363,8 @@ static void fs_remount_root(int fsckerr)
|
||||
*/
|
||||
static void fs_finalize(void)
|
||||
{
|
||||
int flags = MS_NOEXEC | MS_NOSUID;
|
||||
|
||||
/*
|
||||
* Some systems rely on us to both create /dev/shm and, to mount
|
||||
* a tmpfs there. Any system with dbus needs shared memory, so
|
||||
@@ -362,8 +372,8 @@ static void fs_finalize(void)
|
||||
* the /etc/fstab file already.
|
||||
*/
|
||||
if (!fismnt("/dev/shm")) {
|
||||
makedir("/dev/shm", 0777);
|
||||
fs_mount("shm", "/dev/shm", "tmpfs", 0, "mode=0777");
|
||||
makedir("/dev/shm", 1777);
|
||||
fs_mount("shm", "/dev/shm", "tmpfs", flags | MS_NODEV, "mode=1777");
|
||||
}
|
||||
|
||||
/* Modern systems use /dev/pts */
|
||||
@@ -381,7 +391,13 @@ static void fs_finalize(void)
|
||||
snprintf(opts, sizeof(opts), "gid=%d,mode=%d,ptmxmode=0666", gid, mode);
|
||||
|
||||
makedir("/dev/pts", 0755);
|
||||
fs_mount("devpts", "/dev/pts", "devpts", MS_NOSUID | MS_NOEXEC, opts);
|
||||
fs_mount("devpts", "/dev/pts", "devpts", flags, opts);
|
||||
}
|
||||
|
||||
/* Needed on systems like Alpine Linux */
|
||||
if (!fismnt("/dev/mqueue")) {
|
||||
makedir("/dev/mqueue", 1777);
|
||||
fs_mount("mqueue", "/dev/mqueue", "tmpfs", flags | MS_NODEV, NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -393,7 +409,7 @@ static void fs_finalize(void)
|
||||
* To override any of this behavior, add entries to /etc/fstab
|
||||
* for /run (and optionally /run/lock).
|
||||
*/
|
||||
if (fisdir("/run") && !fismnt("/run")) {
|
||||
if (fisdir("/run") && !fismnt("/run") && !fistmpfs("/run")) {
|
||||
fs_mount("tmpfs", "/run", "tmpfs", MS_NOSUID | MS_NODEV | MS_NOEXEC | MS_RELATIME, "mode=0755,size=10%");
|
||||
|
||||
/* This prevents user DoS of /run by filling /run/lock at the expense of another tmpfs, max 5MiB */
|
||||
@@ -402,7 +418,7 @@ static void fs_finalize(void)
|
||||
}
|
||||
|
||||
/* Modern systems use tmpfs for /tmp */
|
||||
if (!fismnt("/tmp"))
|
||||
if (!fismnt("/tmp") && !fistmpfs("/tmp"))
|
||||
fs_mount("tmpfs", "/tmp", "tmpfs", MS_NOSUID | MS_NODEV, "mode=1777");
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
/* Finit - Fast /sbin/init replacement w/ I/O, hook & service plugins
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+4
-1
@@ -1,6 +1,6 @@
|
||||
/* Initialize and serve a login terminal
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -121,6 +121,9 @@ static int osrel(struct osrel *rel)
|
||||
snprintf(rel->version, sizeof(rel->version), "(%s)", codename);
|
||||
}
|
||||
|
||||
if (rel->id[0] && !strcmp(rel->id, "alpine"))
|
||||
return 1; /* compat mode for \r et al. */
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
+11
-10
@@ -1,7 +1,7 @@
|
||||
/* Misc. utility functions for finit and its plugins
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -522,9 +522,10 @@ void networking(int updown)
|
||||
|
||||
pid = fork();
|
||||
if (pid == 0) {
|
||||
int rc = EX_OSERR;
|
||||
const char *cmd;
|
||||
char buf[256];
|
||||
FILE *pp;
|
||||
int rc;
|
||||
|
||||
setsid();
|
||||
sig_unblock();
|
||||
@@ -539,16 +540,16 @@ void networking(int updown)
|
||||
cmd = "ifdown -a -f 2>&1";
|
||||
|
||||
pp = popen(cmd, "r");
|
||||
if (pp) {
|
||||
char buf[256];
|
||||
if (!pp)
|
||||
_exit(EX_OSERR);
|
||||
|
||||
while (fgets(buf, sizeof(buf), pp))
|
||||
logit(LOG_NOTICE, "network: %s", chomp(buf));
|
||||
while (fgets(buf, sizeof(buf), pp))
|
||||
logit(LOG_NOTICE, "network: %s", chomp(buf));
|
||||
|
||||
rc = pclose(pp);
|
||||
}
|
||||
|
||||
_exit(rc);
|
||||
rc = pclose(pp);
|
||||
if (rc == -1)
|
||||
_exit(EX_OSERR);
|
||||
_exit(WEXITSTATUS(rc));
|
||||
}
|
||||
cgroup_service("network", pid, NULL);
|
||||
print(pid > 0 ? 0 : 1, "%s network interfaces ...",
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
/* Misc. utility functions and C-library extensions for finit and its plugins
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* New client tool, replaces old /dev/initctl API and telinit tool
|
||||
*
|
||||
* Copyright (c) 2015-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2015-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* New client tool, replaces old /dev/initctl API and telinit tool
|
||||
*
|
||||
* Copyright (c) 2015-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2015-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
/* inotify watcher for files or directories
|
||||
*
|
||||
* Copyright (c) 2015-2016 Tobias Waldekranz <tobias@waldekranz.com>
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
/* inotify watcher for files or directories
|
||||
*
|
||||
* Copyright (c) 2015-2016 Tobias Waldekranz <tobias@waldekranz.com>
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Listens to kernel events like AC power status and manages sys/ conditions
|
||||
*
|
||||
* Copyright (c) 2021-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2021-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* Finit daemon log functions
|
||||
*
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -42,8 +42,6 @@ static int loglevel = LOG_INFO;
|
||||
|
||||
void log_init(void)
|
||||
{
|
||||
ttinit();
|
||||
|
||||
if (debug)
|
||||
loglevel = LOG_DEBUG;
|
||||
else
|
||||
@@ -53,13 +51,6 @@ void log_init(void)
|
||||
/* If we enabled terse mode at boot, restore to previous setting at shutdown */
|
||||
void log_exit(void)
|
||||
{
|
||||
/*
|
||||
* Unless in debug mode at shutdown, Reinitialize screen,
|
||||
* terminal may have been resized at runtime
|
||||
*/
|
||||
if (!debug)
|
||||
ttinit();
|
||||
|
||||
enable_progress(1);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* Finit daemon log functions
|
||||
*
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2018-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2018-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 2018-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2018-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+8
-6
@@ -1,6 +1,6 @@
|
||||
/* Handle MD arrays
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -28,6 +28,7 @@
|
||||
#include <string.h>
|
||||
|
||||
#include "helpers.h"
|
||||
#include "util.h"
|
||||
|
||||
|
||||
static glob_t *get_arrays(void)
|
||||
@@ -48,17 +49,18 @@ static glob_t *get_arrays(void)
|
||||
*/
|
||||
void mdadm_wait(void)
|
||||
{
|
||||
size_t i;
|
||||
glob_t *gl;
|
||||
char cmd[160];
|
||||
|
||||
/* Setup kernel specific settings, e.g. allow broadcast ping, etc. */
|
||||
gl = get_arrays();
|
||||
if (gl) {
|
||||
for (i = 0; i < gl->gl_pathc; i++) {
|
||||
char *array;
|
||||
size_t i;
|
||||
|
||||
array = basename(gl->gl_pathv[i]);
|
||||
for (i = 0; i < gl->gl_pathc; i++) {
|
||||
const char *array;
|
||||
char cmd[160];
|
||||
|
||||
array = basenm(gl->gl_pathv[i]);
|
||||
snprintf(cmd, sizeof(cmd), "mdadm --wait-clean /dev/%s >/dev/null", array);
|
||||
run_interactive(cmd, "Marking MD array %s as clean", array);
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Mount and unmount helpers
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* PID and PID file helpers
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* PID and PID file helpers
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+13
-9
@@ -1,6 +1,6 @@
|
||||
/* Plugin based services architecture for finit
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -43,6 +43,7 @@
|
||||
#include "private.h"
|
||||
#include "service.h"
|
||||
#include "sig.h"
|
||||
#include "util.h"
|
||||
|
||||
#define is_io_plugin(p) ((p)->io.cb && (p)->io.fd > 0)
|
||||
#define SEARCH_PLUGIN(str) \
|
||||
@@ -77,23 +78,26 @@ static char *trim_ext(char *name)
|
||||
|
||||
int plugin_register(plugin_t *plugin)
|
||||
{
|
||||
const char *nm;
|
||||
|
||||
if (!plugin) {
|
||||
errno = EINVAL;
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Setup default name if none is provided */
|
||||
if (!plugin->name) {
|
||||
nm = plugin->name;
|
||||
if (!nm) {
|
||||
#ifndef ENABLE_STATIC
|
||||
Dl_info info;
|
||||
|
||||
if (dladdr(plugin, &info) && info.dli_fname)
|
||||
plugin->name = basename(info.dli_fname);
|
||||
nm = basenm(info.dli_fname);
|
||||
#endif
|
||||
if (!plugin->name)
|
||||
plugin->name = "unknown";
|
||||
if (!nm)
|
||||
nm = "unknown";
|
||||
}
|
||||
plugin->name = trim_ext(strdup(plugin->name));
|
||||
plugin->name = trim_ext(strdup(nm));
|
||||
|
||||
/* Already registered? */
|
||||
if (plugin_find(plugin->name)) {
|
||||
@@ -253,7 +257,7 @@ void plugin_run_hook(hook_point_t no, void *arg)
|
||||
|
||||
PLUGIN_ITERATOR(p, tmp) {
|
||||
if (p->hook[no].cb) {
|
||||
dbg("Calling %s hook n:o %d (arg: %p) ...", basename(p->name), no, arg ?: "NIL");
|
||||
dbg("Calling %s hook n:o %d (arg: %p) ...", basenm(p->name), no, arg ?: "NIL");
|
||||
p->hook[no].cb(arg ? arg : p->hook[no].arg);
|
||||
}
|
||||
}
|
||||
@@ -301,9 +305,9 @@ int plugin_io_init(plugin_t *p)
|
||||
if (!is_io_plugin(p))
|
||||
return 0;
|
||||
|
||||
dbg("Initializing plugin %s for I/O", basename(p->name));
|
||||
dbg("Initializing plugin %s for I/O", basenm(p->name));
|
||||
if (uev_io_init(ctx, &p->watcher, generic_io_cb, p, p->io.fd, p->io.flags)) {
|
||||
warn("Failed setting up I/O plugin %s", basename(p->name));
|
||||
warn("Failed setting up I/O plugin %s", basenm(p->name));
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Plugin based services architecture for finit
|
||||
*
|
||||
* Copyright (c) 2012-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2012-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
/* Private header file for main finit daemon, not for plugins
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* reboot, halt, poweroff, shutdown, suspend for finit
|
||||
*
|
||||
* Copyright (c) 2009-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2009-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+18
-6
@@ -26,18 +26,27 @@
|
||||
#else
|
||||
#include <sys/prctl.h>
|
||||
|
||||
const char *active_msg = NULL;
|
||||
int interactive = 1;
|
||||
int debug;
|
||||
|
||||
static void print_desc(const char *prefix, const char *msg)
|
||||
{
|
||||
fprintf(stderr, "\e[1m[\e[0m\e[1;33m ⋯ \e[0m\e[1m]\e[0m %s %s", prefix, msg);
|
||||
if (interactive)
|
||||
fprintf(stderr, "\e[1m[\e[0m\e[1;33m ⋯ \e[0m\e[1m]\e[0m %s %s", prefix, msg);
|
||||
else
|
||||
fprintf(stderr, "%s %s ...\n", prefix, msg);
|
||||
active_msg = msg;
|
||||
}
|
||||
static void print_result(int rc)
|
||||
{
|
||||
if (rc)
|
||||
fputs("\r\e[1m[\e[0m\e[1;31mFAIL\e[0m\e[1m]\e[0m\n", stderr);
|
||||
else
|
||||
fputs("\r\e[1m[\e[0m\e[1;32m OK \e[0m\e[1m]\e[0m\n", stderr);
|
||||
if (interactive) {
|
||||
if (rc)
|
||||
fputs("\r\e[1m[\e[0m\e[1;31mFAIL\e[0m\e[1m]\e[0m\n", stderr);
|
||||
else
|
||||
fputs("\r\e[1m[\e[0m\e[1;32m OK \e[0m\e[1m]\e[0m\n", stderr);
|
||||
} else
|
||||
fprintf(stderr, "[%s] %s\n", rc ? "FAIL" : " OK ", active_msg ?: "");
|
||||
}
|
||||
|
||||
void sig_unblock(void)
|
||||
@@ -193,8 +202,11 @@ int main(int argc, char *argv[])
|
||||
int rc, c, progress = 0, sysv = 0;
|
||||
char *dir;
|
||||
|
||||
while ((c = getopt(argc, argv, "dh?ps")) != EOF) {
|
||||
while ((c = getopt(argc, argv, "bdh?ps")) != EOF) {
|
||||
switch(c) {
|
||||
case 'b': /* batch mode */
|
||||
interactive = 0;
|
||||
break;
|
||||
case 'd':
|
||||
debug = 1;
|
||||
break;
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Work queue helper functions
|
||||
*
|
||||
* Copyright (c) 2018-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2018-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Work queue helper functions
|
||||
*
|
||||
* Copyright (c) 2018-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2018-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+47
-28
@@ -1,6 +1,6 @@
|
||||
/* List and enable/disable service configurations
|
||||
*
|
||||
* Copyright (c) 2017-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2017-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -222,20 +222,13 @@ int serv_list(char *arg)
|
||||
* If the resulting file doesn't exist, and creat is not set, *or*
|
||||
* the base directory doesn't exist, we return NULL.
|
||||
.*/
|
||||
static char *conf(char *path, size_t len, char *name, int creat)
|
||||
static char *conf(char *path, size_t len, char *name, int creat, int template)
|
||||
{
|
||||
char corr[40];
|
||||
|
||||
if (!name || !name[0] || !strcmp(name, "finit") || !strcmp(name, "finit.conf")) {
|
||||
strlcpy(path, finit_conf, len);
|
||||
return path;
|
||||
}
|
||||
|
||||
if (!strstr(name, ".conf")) {
|
||||
snprintf(corr, sizeof(corr), "%s.conf", name);
|
||||
name = corr;
|
||||
}
|
||||
|
||||
if (!fisdir(finit_rcsd))
|
||||
return NULL;
|
||||
|
||||
@@ -243,14 +236,25 @@ static char *conf(char *path, size_t len, char *name, int creat)
|
||||
if (!fisdir(path)) {
|
||||
if (creat && mkdir(path, 0755) && errno != EEXIST)
|
||||
return NULL;
|
||||
else
|
||||
paste(path, len, finit_rcsd, name);
|
||||
paste(path, len, finit_rcsd, name);
|
||||
} else
|
||||
strlcat(path, name, len);
|
||||
|
||||
if (suffix(path, len, ".conf"))
|
||||
return NULL;
|
||||
|
||||
/* fall back to static service unless edit/create */
|
||||
if (!creat && !fexist(path))
|
||||
paste(path, len, finit_rcsd, name);
|
||||
if (!creat && !fexist(path)) {
|
||||
char *at = strchr(path, '@');
|
||||
|
||||
if (template && at)
|
||||
*++at = 0;
|
||||
else
|
||||
paste(path, len, finit_rcsd, name);
|
||||
|
||||
if (suffix(path, len, ".conf"))
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return path;
|
||||
}
|
||||
@@ -336,14 +340,14 @@ int do_disable(char *arg, int check)
|
||||
return serv_list("available");
|
||||
}
|
||||
|
||||
len = strlen(arg);
|
||||
serv = alloca(len + 6);
|
||||
len = strlen(arg) + 7;
|
||||
serv = alloca(len);
|
||||
if (!serv)
|
||||
ERR(71, "failed allocating stack");
|
||||
|
||||
strlcpy(serv, arg, len + 6);
|
||||
if (len < 6 || strcmp(&serv[len - 5], ".conf"))
|
||||
strlcat(serv, ".conf", len + 6);
|
||||
strlcpy(serv, arg, len);
|
||||
if (suffix(serv, len, ".conf"))
|
||||
ERR(71, "failed composing service name (%s)", serv);
|
||||
|
||||
if (chdir(finit_rcsd))
|
||||
ERR(72, "failed cd %s", finit_rcsd);
|
||||
@@ -374,20 +378,30 @@ int serv_touch(char *arg)
|
||||
return serv_list("enabled");
|
||||
}
|
||||
|
||||
fn = conf(path, sizeof(path), arg, 0);
|
||||
/* 1. Try /etc/finit.d/enabled/$arg.conf to handle template@.conf */
|
||||
paste(path, sizeof(path), finit_rcsd, "enabled/");
|
||||
strlcat(path, arg, sizeof(path));
|
||||
if (!suffix(path, sizeof(path), ".conf") && fexist(path)) {
|
||||
fn = path;
|
||||
goto touchit;
|
||||
}
|
||||
|
||||
/* 2. Try /etc/finit.d/available/$arg.conf and other combos (legacy) */
|
||||
fn = conf(path, sizeof(path), arg, 0, 0);
|
||||
if (!fexist(fn)) {
|
||||
if (!strstr(arg, "finit.conf"))
|
||||
ERRX(72, "%s not available.", arg);
|
||||
ERRX(noerr ? 0 : 72, "%s not available.", arg);
|
||||
if (is_builtin(arg))
|
||||
ERRX(4, "%s is a built-in service.", arg);
|
||||
ERRX(noerr ? 0 : 4, "%s is a built-in service.", arg);
|
||||
|
||||
strlcpy(path, finit_conf, sizeof(path));
|
||||
fn = path;
|
||||
}
|
||||
|
||||
touchit:
|
||||
/* libite:touch() follows symlinks */
|
||||
if (utimensat(AT_FDCWD, fn, NULL, AT_SYMLINK_NOFOLLOW))
|
||||
ERR(71, "failed marking %s for reload", fn);
|
||||
ERR(noerr ? 0 : 71, "failed marking %s for reload", fn);
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -397,13 +411,18 @@ int serv_show(char *arg)
|
||||
char path[256];
|
||||
char *fn;
|
||||
|
||||
fn = conf(path, sizeof(path), arg, 0);
|
||||
fn = conf(path, sizeof(path), arg, 0, 0);
|
||||
if (!fexist(fn)) {
|
||||
if (is_builtin(arg))
|
||||
ERRX(4, "%s is a built-in service.", arg);
|
||||
|
||||
WARNX("Cannot find %s", arg);
|
||||
return 1;
|
||||
fn = conf(path, sizeof(path), arg, 0, 1);
|
||||
if (!fn || !fexist(fn)) {
|
||||
WARNX("Cannot find %s", arg);
|
||||
return 1;
|
||||
}
|
||||
|
||||
return systemf("cat %s | sed 's/%%i/system/g'", fn);
|
||||
}
|
||||
|
||||
return systemf("cat %s", fn);
|
||||
@@ -434,7 +453,7 @@ static int do_edit(char *arg, int creat)
|
||||
char path[256];
|
||||
char *fn;
|
||||
|
||||
fn = conf(path, sizeof(path), arg, creat);
|
||||
fn = conf(path, sizeof(path), arg, creat, 0);
|
||||
if (!fexist(fn)) {
|
||||
if (is_builtin(arg))
|
||||
ERRX(4, "%s is a built-in service.", arg);
|
||||
@@ -488,7 +507,7 @@ int serv_creat(char *arg)
|
||||
return do_edit(arg, 1);
|
||||
|
||||
/* Open fn for writing from pipe */
|
||||
fn = conf(buf, sizeof(buf), arg, 1);
|
||||
fn = conf(buf, sizeof(buf), arg, 1, 0);
|
||||
if (!fn)
|
||||
ERR(73, "failed creating conf %s", arg);
|
||||
|
||||
@@ -517,7 +536,7 @@ int serv_delete(char *arg)
|
||||
return serv_list("available");
|
||||
}
|
||||
|
||||
fn = conf(buf, sizeof(buf), arg, 0);
|
||||
fn = conf(buf, sizeof(buf), arg, 0, 0);
|
||||
if (!fn) {
|
||||
if (is_builtin(arg))
|
||||
ERRX(4, "%s is a built-in service.", arg);
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* List and enable/disable service configurations
|
||||
*
|
||||
* Copyright (c) 2017-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2017-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+49
-41
@@ -1,7 +1,7 @@
|
||||
/* Finit service monitor, task starter and generic API for managing svc_t
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -330,14 +330,15 @@ static int lredirect(svc_t *svc)
|
||||
|
||||
snprintf(rot, sizeof(rot), "%d:%d", logfile_size_max, logfile_count_max);
|
||||
snprintf(pid, sizeof(pid), "%d", svc_pid);
|
||||
execlp("logger", "logger", "-f", svc->log.file, "-b", "-t", tag, "-p", prio, debug ? "-s" : "", "-I", pid, "-r", rot, NULL);
|
||||
execlp("logger", "logger", "-f", svc->log.file, "-b", "-t", tag, "-p", prio, "-I", pid, "-r", rot, debug ? "-s" : NULL, NULL);
|
||||
} else {
|
||||
char sz[20], num[3];
|
||||
|
||||
snprintf(sz, sizeof(sz), "%d", logfile_size_max);
|
||||
snprintf(num, sizeof(num), "%d", logfile_count_max);
|
||||
|
||||
execlp(_PATH_LOGIT, "logit", "-f", svc->log.file, "-n", sz, "-r", num, debug ? "-s" : "", NULL);
|
||||
execlp(_PATH_LOGIT, "logit", "-f", svc->log.file, "-n", sz, "-r", num, debug ? "-s" : NULL, NULL);
|
||||
|
||||
}
|
||||
_exit(1);
|
||||
}
|
||||
@@ -351,9 +352,9 @@ static int lredirect(svc_t *svc)
|
||||
char pid[16];
|
||||
|
||||
snprintf(pid, sizeof(pid), "%d", svc_pid);
|
||||
execlp("logger", "logger", "-t", tag, "-p", prio, debug ? "-s" : "", "-I", pid, NULL);
|
||||
execlp("logger", "logger", "-t", tag, "-p", prio, "-I", pid, debug ? "-s" : NULL, NULL);
|
||||
} else {
|
||||
execlp(_PATH_LOGIT, "logit", "-t", tag, "-p", prio, debug ? "-s" : "", NULL);
|
||||
execlp(_PATH_LOGIT, "logit", "-t", tag, "-p", prio, debug ? "-s" : NULL, NULL);
|
||||
}
|
||||
_exit(1);
|
||||
}
|
||||
@@ -1002,7 +1003,7 @@ int service_stop(svc_t *svc)
|
||||
return 0;
|
||||
}
|
||||
|
||||
dbg("Sending %s to pid:%d name:%s", sig, svc->pid, nm);
|
||||
dbg("Sending %s to pid:%d name:%s(%s)", sig, svc->pid, id, nm);
|
||||
logit(LOG_CONSOLE | LOG_NOTICE, "Stopping %s[%d], sending %s ...", id, svc->pid, sig);
|
||||
} else {
|
||||
logit(LOG_CONSOLE | LOG_NOTICE, "Calling '%s stop' ...", cmdline);
|
||||
@@ -1620,7 +1621,7 @@ int service_register(int type, char *cfg, struct rlimit rlimit[], char *file)
|
||||
strlcat(ident, id, sizeof(ident));
|
||||
}
|
||||
|
||||
if (ifstmt && !svc_ifthen(1, ident, ifstmt))
|
||||
if (ifstmt && !svc_ifthen(1, ident, ifstmt, nowarn))
|
||||
return 0;
|
||||
|
||||
levels = conf_parse_runlevels(runlevels);
|
||||
@@ -1631,11 +1632,18 @@ int service_register(int type, char *cfg, struct rlimit rlimit[], char *file)
|
||||
}
|
||||
|
||||
if (type == SVC_TYPE_TTY) {
|
||||
size_t i, len = 0;
|
||||
size_t i, len;
|
||||
char *ptr;
|
||||
|
||||
if (tty_parse_args(&tty, cmd, &args))
|
||||
return errno;
|
||||
|
||||
if (tty_isatcon(tty.dev))
|
||||
dev = tty_atcon();
|
||||
else
|
||||
dev = tty.dev;
|
||||
next:
|
||||
len = 0;
|
||||
if (tty.cmd)
|
||||
len += strlen(tty.cmd);
|
||||
else
|
||||
@@ -1658,14 +1666,22 @@ int service_register(int type, char *cfg, struct rlimit rlimit[], char *file)
|
||||
if (!cmd)
|
||||
return errno;
|
||||
|
||||
if (tty_isatcon(tty.dev))
|
||||
dev = tty_atcon();
|
||||
else
|
||||
dev = tty.dev;
|
||||
|
||||
/* tty's always respawn, never incr. restart_cnt */
|
||||
respawn = 1;
|
||||
next:
|
||||
|
||||
/* Create name:id tuple for identity, e.g., tty:S0 */
|
||||
ptr = strrchr(dev, '/');
|
||||
if (ptr)
|
||||
ptr++;
|
||||
else
|
||||
ptr = dev;
|
||||
if (!strncmp(ptr, "tty", 3))
|
||||
ptr += 3;
|
||||
|
||||
name = "tty";
|
||||
if (!id || id[0] == 0)
|
||||
id = ptr;
|
||||
|
||||
svc = svc_find_by_tty(dev);
|
||||
} else
|
||||
svc = svc_find(name, id);
|
||||
@@ -1721,8 +1737,6 @@ int service_register(int type, char *cfg, struct rlimit rlimit[], char *file)
|
||||
conf_parse_cond(svc, cond);
|
||||
|
||||
if (type == SVC_TYPE_TTY) {
|
||||
char *ptr;
|
||||
|
||||
if (dev)
|
||||
strlcpy(svc->dev, dev, sizeof(svc->dev));
|
||||
if (tty.baud)
|
||||
@@ -1737,19 +1751,6 @@ int service_register(int type, char *cfg, struct rlimit rlimit[], char *file)
|
||||
|
||||
/* TTYs cannot be redirected */
|
||||
log = NULL;
|
||||
|
||||
/* Create name:id tuple for identity, e.g., tty:S0 */
|
||||
ptr = strrchr(svc->dev, '/');
|
||||
if (ptr)
|
||||
ptr++;
|
||||
else
|
||||
ptr = svc->dev;
|
||||
if (!strncmp(ptr, "tty", 3))
|
||||
ptr += 3;
|
||||
if (!id || id[0] == 0)
|
||||
id = ptr;
|
||||
strlcpy(svc->name, "tty", sizeof(svc->name));
|
||||
strlcpy(svc->id, id, sizeof(svc->id));
|
||||
}
|
||||
|
||||
parse_cmdline_args(svc, cmd, &args);
|
||||
@@ -1869,8 +1870,10 @@ int service_register(int type, char *cfg, struct rlimit rlimit[], char *file)
|
||||
/* continue expanding any 'tty @console ...' */
|
||||
if (tty_isatcon(tty.dev)) {
|
||||
dev = tty_atcon();
|
||||
if (dev)
|
||||
if (dev) {
|
||||
id = NULL; /* reset for next tty:ID */
|
||||
goto next;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
@@ -2027,7 +2030,7 @@ void service_mark_unavail(void)
|
||||
if (!svc->ifstmt[0])
|
||||
continue;
|
||||
|
||||
if (!svc_ifthen(1, svc_ident(svc, buf, sizeof(buf)), svc->ifstmt))
|
||||
if (!svc_ifthen(1, svc_ident(svc, buf, sizeof(buf)), svc->ifstmt, svc->nowarn))
|
||||
svc_mark(svc);
|
||||
}
|
||||
}
|
||||
@@ -2260,7 +2263,7 @@ static void svc_set_state(svc_t *svc, svc_state_t new_state)
|
||||
/* if PID isn't collected within SVC_TERM_TIMEOUT msec, kill it! */
|
||||
if (new_state == SVC_STOPPING_STATE) {
|
||||
dbg("%s is stopping, wait %d sec before sending SIGKILL ...",
|
||||
svc_ident(svc, NULL, 0), svc->killdelay / 1000);
|
||||
svc_ident(svc, NULL, 0), svc->killdelay / 1000);
|
||||
service_timeout_cancel(svc);
|
||||
service_timeout_after(svc, svc->killdelay, service_kill);
|
||||
}
|
||||
@@ -2298,6 +2301,8 @@ static void svc_set_state(svc_t *svc, svc_state_t new_state)
|
||||
if ((old_state == SVC_RUNNING_STATE && new_state == SVC_PAUSED_STATE) ||
|
||||
(old_state == SVC_PAUSED_STATE && new_state == SVC_RUNNING_STATE))
|
||||
; /* only paused during reload, don't clear conds. */
|
||||
else if (sm_is_in_teardown(&sm))
|
||||
cond_clear_noupdate(cond);
|
||||
else
|
||||
cond_clear(cond);
|
||||
|
||||
@@ -2329,8 +2334,8 @@ void service_forked(svc_t *svc)
|
||||
svc_set_state(svc, SVC_RUNNING_STATE);
|
||||
}
|
||||
|
||||
/* Set service/foo/ready condition for services and call optional ready:script */
|
||||
void service_ready(svc_t *svc)
|
||||
/* Set or clear service/foo/ready condition for services and call optional ready:script */
|
||||
void service_ready(svc_t *svc, int ready)
|
||||
{
|
||||
char buf[MAX_COND_LEN];
|
||||
|
||||
@@ -2338,10 +2343,13 @@ void service_ready(svc_t *svc)
|
||||
return;
|
||||
|
||||
snprintf(buf, sizeof(buf), "service/%s/ready", svc_ident(svc, NULL, 0));
|
||||
cond_set(buf);
|
||||
if (ready) {
|
||||
cond_set(buf);
|
||||
|
||||
if (svc_has_ready(svc))
|
||||
service_ready_script(svc);
|
||||
if (svc_has_ready(svc))
|
||||
service_ready_script(svc);
|
||||
} else
|
||||
cond_clear(buf);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -2550,7 +2558,7 @@ restart:
|
||||
svc_mark_clean(svc);
|
||||
}
|
||||
if (svc->notify == SVC_NOTIFY_NONE)
|
||||
service_ready(svc);
|
||||
service_ready(svc, 1);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
@@ -2584,7 +2592,7 @@ restart:
|
||||
}
|
||||
|
||||
dbg("Reassert %s ready condition", svc_ident(svc, NULL, 0));
|
||||
service_ready(svc);
|
||||
service_ready(svc, 1);
|
||||
}
|
||||
break;
|
||||
|
||||
@@ -2720,7 +2728,7 @@ void service_notify_reconf(void)
|
||||
if (svc->notify != SVC_NOTIFY_NONE && (svc_is_changed(svc) || svc_is_starting(svc)))
|
||||
continue;
|
||||
|
||||
service_ready(svc);
|
||||
service_ready(svc, 1);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2761,7 +2769,7 @@ void service_notify_cb(uev_t *w, void *arg, int events)
|
||||
* the service_notify_reconf() function to step the
|
||||
* generation of the READY condition.
|
||||
*/
|
||||
service_ready(svc);
|
||||
service_ready(svc, 1);
|
||||
|
||||
/* s6 applications close their socket after notification */
|
||||
if (svc->notify == SVC_NOTIFY_S6) {
|
||||
|
||||
+2
-2
@@ -1,7 +1,7 @@
|
||||
/* Finit service monitor, task starter and generic API for managing svc_t
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -42,7 +42,7 @@ int service_timeout_after (svc_t *svc, int timeout, void (*cb)(svc_t *svc
|
||||
int service_timeout_cancel (svc_t *svc);
|
||||
|
||||
void service_forked (svc_t *svc);
|
||||
void service_ready (svc_t *svc);
|
||||
void service_ready (svc_t *svc, int ready);
|
||||
|
||||
int service_stop (svc_t *svc);
|
||||
int service_step (svc_t *svc);
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* Signal management - Be conservative with what finit responds to!
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* Signal management - Be conservative with what finit responds to!
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -316,9 +316,11 @@ restart:
|
||||
/* Cleanup stale services */
|
||||
svc_clean_dynamic(service_unregister);
|
||||
|
||||
#ifdef FINIT_RC_LOCAL
|
||||
/* Compat SysV init */
|
||||
if (prevlevel == INIT_LEVEL && !rescue)
|
||||
run_bg(FINIT_RC_LOCAL, NULL);
|
||||
#endif
|
||||
|
||||
/*
|
||||
* "I've seen things you people wouldn't believe. Attack ships on fire off
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Reset terminal line settings (stty sane)
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* poor man's sulogin, may be statically linked
|
||||
*
|
||||
* Copyright (c) 2021-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2021-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* Low-level service primitives and generic API for managing svc_t structures
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -649,7 +649,7 @@ int svc_enabled(svc_t *svc)
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!svc_ifthen(0, NULL, svc->ifstmt)) {
|
||||
if (!svc_ifthen(0, NULL, svc->ifstmt, svc->nowarn)) {
|
||||
// dbg("ifthen:%s>", svc->ifstmt[0] ? svc->ifstmt : "<");
|
||||
return 0;
|
||||
}
|
||||
@@ -704,11 +704,12 @@ int svc_conflicts(svc_t *svc)
|
||||
* @is_conf: Set when called by service_mark_unavail()
|
||||
* @ident: svc_t identififcation (name:id)
|
||||
* @stmt: if: statement from .conf file
|
||||
* @quiet: If non-zero, do not warn in syslog
|
||||
*
|
||||
* Returns:
|
||||
* %TRUE(1) yes, use this svc_t, %FALSE(0) prune
|
||||
*/
|
||||
int svc_ifthen(int is_conf, const char *ident, char *stmt)
|
||||
int svc_ifthen(int is_conf, const char *ident, char *stmt, int quiet)
|
||||
{
|
||||
char stmts[MAX_IDENT_LEN];
|
||||
int not = 0;
|
||||
@@ -758,11 +759,13 @@ int svc_ifthen(int is_conf, const char *ident, char *stmt)
|
||||
|
||||
svc = svc_find_by_str(stmt);
|
||||
if (not && svc) {
|
||||
logit(LOG_NOTICE, "skipping %s, %s already loaded.", ident, svc_ident(svc, NULL, 0));
|
||||
if (!quiet)
|
||||
logit(LOG_NOTICE, "skipping %s, %s already loaded.", ident, svc_ident(svc, NULL, 0));
|
||||
return 0;
|
||||
}
|
||||
if (!not && !svc) {
|
||||
logit(LOG_NOTICE, "skipping %s, %s not available.", ident, stmt);
|
||||
if (!quiet)
|
||||
logit(LOG_NOTICE, "skipping %s, %s not available.", ident, stmt);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* Low-level service primitives and generic API for managing svc_t structures
|
||||
*
|
||||
* Copyright (c) 2008-2010 Claudio Matsuoka <cmatsuoka@gmail.com>
|
||||
* Copyright (c) 2008-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2008-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -249,7 +249,7 @@ void svc_prune_bootstrap (void);
|
||||
void svc_enable (svc_t *svc);
|
||||
int svc_enabled (svc_t *svc);
|
||||
int svc_conflicts (svc_t *svc);
|
||||
int svc_ifthen (int is_conf, const char *ident, char *stmt);
|
||||
int svc_ifthen (int is_conf, const char *ident, char *stmt, int quiet);
|
||||
|
||||
int svc_parse_jobstr (char *str, size_t len, void *user_data, int (*found)(svc_t *, void *), int (not_found)(char *, char *, void *));
|
||||
|
||||
@@ -271,6 +271,7 @@ static inline void svc_starting (svc_t *svc) { if (svc) svc->starting = 1;
|
||||
static inline void svc_started (svc_t *svc) { if (svc) svc->starting = 0; }
|
||||
static inline int svc_is_starting (svc_t *svc) { return svc && 0 != svc->starting; }
|
||||
static inline int svc_is_running (svc_t *svc) { return svc && svc->state == SVC_RUNNING_STATE; }
|
||||
static inline int svc_is_stopping (svc_t *svc) { return svc && svc->state == SVC_STOPPING_STATE; }
|
||||
|
||||
static inline int svc_is_removed (svc_t *svc) { return svc && svc->removed; }
|
||||
static inline int svc_is_changed (svc_t *svc) { return svc && 0 != svc->dirty; }
|
||||
|
||||
+9
-5
@@ -1,6 +1,6 @@
|
||||
/* Limited tmpfiles.d implementation
|
||||
*
|
||||
* Copyright (c) 2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -78,8 +78,8 @@ static int do_delete(const char *fpath, const struct stat *sb, int tflag, struct
|
||||
if (ftw->level == 0)
|
||||
return 1;
|
||||
|
||||
if (remove(fpath))
|
||||
warn("Failed removing condition %s", fpath);
|
||||
if (remove(fpath) && errno != EBUSY)
|
||||
warn("Failed removing %s", fpath);
|
||||
|
||||
return 0;
|
||||
|
||||
@@ -90,7 +90,7 @@ static int rmrf(const char *path)
|
||||
if (!fisdir(path))
|
||||
return 0;
|
||||
|
||||
nftw(path, do_delete, 20, FTW_DEPTH);
|
||||
nftw(path, do_delete, 20, FTW_DEPTH | FTW_PHYS);
|
||||
if (remove(path) && errno != ENOENT)
|
||||
warn("Failed removing path %s", path);
|
||||
|
||||
@@ -434,6 +434,10 @@ static void tmpfiles(char *line)
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 'X':
|
||||
case 'x':
|
||||
dbg("Unsupported x/X command, ignoring %s, no support for clean at runtime.", path);
|
||||
break;
|
||||
case 'Z':
|
||||
opts = "-R";
|
||||
/* fallthrough */
|
||||
@@ -492,7 +496,7 @@ void tmpfilesd(void)
|
||||
|
||||
/* check for overrides */
|
||||
for (j = i + 1; j < gl.gl_pathc; j++) {
|
||||
if (strcmp(basename(fn), basename(gl.gl_pathv[j])))
|
||||
if (strcmp(basenm(fn), basenm(gl.gl_pathv[j])))
|
||||
continue;
|
||||
fn = NULL;
|
||||
break;
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Limited tmpfiles.d implementation
|
||||
*
|
||||
* Copyright (c) 2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* Finit TTY handling
|
||||
*
|
||||
* Copyright (c) 2013 Mattias Walström <lazzer@gmail.com>
|
||||
* Copyright (c) 2013-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2013-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
/* Finit TTY handling
|
||||
*
|
||||
* Copyright (c) 2013 Mattias Walström <lazzer@gmail.com>
|
||||
* Copyright (c) 2013-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2013-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+30
-1
@@ -1,6 +1,6 @@
|
||||
/* Misc. shared utility functions for initctl, reboot and finit
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -42,6 +42,8 @@
|
||||
# include <sys/ioctl.h>
|
||||
#endif
|
||||
#include <sys/sysinfo.h> /* sysinfo() */
|
||||
#include <sys/vfs.h> /* statfs */
|
||||
#include <linux/magic.h>
|
||||
#ifdef _LIBITE_LITE
|
||||
# include <libite/lite.h>
|
||||
#else
|
||||
@@ -151,6 +153,19 @@ char *progname(char *arg0)
|
||||
return prognm;
|
||||
}
|
||||
|
||||
/* basename(3) replacement that does not modify its argument */
|
||||
const char *basenm(const char *path)
|
||||
{
|
||||
const char *basename;
|
||||
|
||||
basename = rindex(path, '/');
|
||||
if (!basename)
|
||||
return path;
|
||||
|
||||
basename++;
|
||||
return basename;
|
||||
}
|
||||
|
||||
char *str(char *fmt, ...)
|
||||
{
|
||||
static char buf[32];
|
||||
@@ -559,6 +574,20 @@ int fismnt(char *dir)
|
||||
return ismnt("/proc/mounts", dir, NULL);
|
||||
}
|
||||
|
||||
/* Return 1 if dir is a backed by tmpfs or overlayfs */
|
||||
int fistmpfs(char *dir)
|
||||
{
|
||||
struct statfs info = {0};
|
||||
|
||||
if (statfs(dir, &info))
|
||||
return 0;
|
||||
|
||||
if (info.f_type == TMPFS_MAGIC || info.f_type == OVERLAYFS_SUPER_MAGIC)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef HAVE_TERMIOS_H
|
||||
/*
|
||||
* Called by initctl, and by finit at boot and shutdown, to
|
||||
|
||||
+23
-1
@@ -1,6 +1,6 @@
|
||||
/* Misc. shared utility functions for initctl, reboot and finit
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -55,6 +55,7 @@ extern char *prognm;
|
||||
#endif
|
||||
|
||||
char *progname (char *arg0);
|
||||
const char *basenm (const char *path);
|
||||
|
||||
char *str (char *fmt, ...) __attribute__ ((format (printf, 1, 2)));
|
||||
int fnread (char *buf, size_t len, char *fmt, ...) __attribute__ ((format (printf, 3, 4)));
|
||||
@@ -79,6 +80,7 @@ void de_dotdot (char *file);
|
||||
|
||||
int ismnt (char *file, char *dir, char *mode);
|
||||
int fismnt (char *dir);
|
||||
int fistmpfs (char *dir);
|
||||
|
||||
#ifdef HAVE_TERMIOS_H
|
||||
int ttinit (void);
|
||||
@@ -108,6 +110,26 @@ static inline int paste(char *buf, size_t len, const char *dir, const char *file
|
||||
fisslashdir(dir) ? "" : file[0] == '/' ? "" : "/", file);
|
||||
}
|
||||
|
||||
/* ensure path has suffix */
|
||||
static inline int suffix(char *path, size_t len, const char *sfx)
|
||||
{
|
||||
size_t slen = strlen(sfx);
|
||||
size_t plen = strlen(path);
|
||||
|
||||
if (plen < slen)
|
||||
slen = strlcat(path, sfx, len);
|
||||
else {
|
||||
plen -= slen;
|
||||
if (strcmp(&path[plen], sfx))
|
||||
slen = strlcat(path, sfx, len);
|
||||
}
|
||||
|
||||
if (slen >= len)
|
||||
return -1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif /* FINIT_UTIL_H_ */
|
||||
|
||||
/**
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* UTMP API
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* UTMP API
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Built-in watchdog daemon
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
/* Built-in watchdog daemon
|
||||
*
|
||||
* Copyright (c) 2016-2023 Joachim Wiberg <troglobit@gmail.com>
|
||||
* Copyright (c) 2016-2024 Joachim Wiberg <troglobit@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
@@ -18,8 +18,10 @@
|
||||
# change the contents any way you like, it can even be empty.
|
||||
|
||||
# Check for systemd-udevd and eudev, if we find both, we opt for the latter.
|
||||
service nowarn [S12345789] cgroup.system name:udevd notify:none pid:udevd log /lib/systemd/systemd-udevd -- Device event daemon (udev)
|
||||
service nowarn [S12345789] cgroup.system name:udevd notify:none pid:udevd log udevd -D -- Device event daemon (udev)
|
||||
service nowarn cgroup.system name:udevd notify:none env:-/etc/default/udevd pid:udevd log \
|
||||
[S12345789] /lib/systemd/systemd-udevd $UDEVD_ARGS -- Device event daemon (udev)
|
||||
service nowarn cgroup.system name:udevd notify:none env:-/etc/default/udevd pid:udevd log \
|
||||
[S12345789] udevd $UDEVD_ARGS -- Device event daemon (udev)
|
||||
|
||||
# Wait for udevd to start, then trigger coldplug events and module loading.
|
||||
# The last 'settle' call waits for it to finalize processing all uevents.
|
||||
|
||||
+5
-1
@@ -11,7 +11,9 @@ EXTRA_DIST = skel/bin/busybox-x86_64.sha256 skel/sbin/service.sh skel/etc/env
|
||||
skel/cdrom/.empty skel/dev/shm/.empty skel/dev/pts/.empty \
|
||||
skel/etc/inittab skel/etc/hostname skel/etc/fstab \
|
||||
skel/etc/init.d/rcS skel/etc/init.d/rcK skel/tmp/.empty \
|
||||
skel/etc/finit.d/.empty skel/sbin/task.sh skel/bin/crasher.sh \
|
||||
skel/etc/finit.d/.empty skel/etc/finit.d/available/.empty \
|
||||
skel/etc/finit.d/enabled/.empty \
|
||||
skel/sbin/task.sh skel/bin/crasher.sh \
|
||||
skel/etc/init.d/S01-service.sh skel/etc/init.d/S02-serv.sh \
|
||||
skel/proc/.empty skel/root/.empty skel/run/.empty \
|
||||
skel/sbin/chrootsetup.sh skel/srv/.empty skel/sys/.empty \
|
||||
@@ -38,6 +40,7 @@ EXTRA_DIST += initctl-status-subset.sh
|
||||
EXTRA_DIST += notify.sh
|
||||
EXTRA_DIST += pidfile.sh
|
||||
EXTRA_DIST += pre-post-serv.sh
|
||||
EXTRA_DIST += process-depends.sh
|
||||
EXTRA_DIST += rclocal.sh
|
||||
EXTRA_DIST += ready-serv.sh
|
||||
EXTRA_DIST += restart-self.sh
|
||||
@@ -83,6 +86,7 @@ TESTS += initctl-status-subset.sh
|
||||
TESTS += notify.sh
|
||||
TESTS += pidfile.sh
|
||||
TESTS += pre-post-serv.sh
|
||||
TESTS += process-depends.sh
|
||||
TESTS += rclocal.sh
|
||||
TESTS += ready-serv.sh
|
||||
TESTS += restart-self.sh
|
||||
|
||||
@@ -96,6 +96,14 @@ assert_nocond()
|
||||
assert "Condition $cond cleared" "$(texec initctl -v cond get "$cond")" = "off"
|
||||
}
|
||||
|
||||
assert_ready()
|
||||
{
|
||||
srv=$1
|
||||
cond="service/$srv/ready"
|
||||
|
||||
assert "$cond asserted" "$(texec initctl cond dump |grep "<$cond>" |awk '{print $3}')" = "on"
|
||||
}
|
||||
|
||||
assert_is_pidfile()
|
||||
{
|
||||
assert "Process has PID file: $2" "$(texec initctl -p status "$1" | awk '/PID file/{print $4}')" = "$2"
|
||||
|
||||
+2
-2
@@ -74,7 +74,7 @@ test_one()
|
||||
# Issue #343; pidfile.so inadvertedly marked systemd services as
|
||||
# 'started' when they created their PID file. The serv test daemon
|
||||
# waits 3 sec between pidfile and notify to trigger this bug.
|
||||
if [ "$type" != "native" ]; then
|
||||
if [ "$type" != "pid" ]; then
|
||||
say "Verify 'ready' is *not* asserted immediately on restart + reload"
|
||||
run "initctl restart serv"
|
||||
run "initctl reload"
|
||||
@@ -103,7 +103,7 @@ test_one()
|
||||
|
||||
#run "initctl debug"
|
||||
|
||||
test_one "native" "service log:stdout serv -np -- pid file readiness"
|
||||
test_one "pid" "service log:stdout notify:pid serv -np -- pid file readiness"
|
||||
test_one "s6" "service log:stdout notify:s6 serv -n -N %n -- s6 readiness"
|
||||
test_one "systemd" "service log:stdout notify:systemd serv -n -- systemd readiness"
|
||||
|
||||
|
||||
+72
-23
@@ -1,4 +1,10 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# Verify pre:script and post:script runs as intended when starting,
|
||||
# stopping and disabling services in various configurations and
|
||||
# conditions.
|
||||
#
|
||||
|
||||
set -eu
|
||||
|
||||
TEST_DIR=$(dirname "$0")
|
||||
@@ -16,6 +22,65 @@ test_teardown()
|
||||
run "rm -f $FINIT_CONF"
|
||||
}
|
||||
|
||||
startit()
|
||||
{
|
||||
service=$1
|
||||
conf=$2
|
||||
pre=$3
|
||||
precont=$4
|
||||
|
||||
say "Add stanza '$service' to $conf ..."
|
||||
run "echo '$service' > $conf"
|
||||
|
||||
if echo "$conf" |grep -q available; then
|
||||
# configlets need must be enabled
|
||||
run "initctl enable serv"
|
||||
fi
|
||||
|
||||
say 'Reload Finit'
|
||||
run "initctl reload"
|
||||
|
||||
# Ensure service has started before checking pre condition
|
||||
retry 'assert_num_children 1 serv'
|
||||
|
||||
# Verify pre:script has run
|
||||
if [ -n "$pre" ]; then
|
||||
assert_file_contains "$pre" "$precont"
|
||||
# Drop pre condition indicator for next test
|
||||
run "rm -f $pre"
|
||||
fi
|
||||
}
|
||||
|
||||
stopit()
|
||||
{
|
||||
conf=$1
|
||||
post=$2
|
||||
postcont=$3
|
||||
|
||||
if echo "$conf" |grep -q available; then
|
||||
say 'Disable service & reload'
|
||||
run "initctl disable serv"
|
||||
run "initctl reload"
|
||||
else
|
||||
say 'Stop the service'
|
||||
run "initctl stop serv"
|
||||
fi
|
||||
|
||||
# Ensure service has stopped before checking for post condition
|
||||
retry 'assert_num_children 0 serv'
|
||||
|
||||
# Verify post:script has run
|
||||
if [ -n "$post" ]; then
|
||||
assert_file_contains "$post" "$postcont"
|
||||
# Drop post condition indicator for next test
|
||||
run "rm -f $post"
|
||||
fi
|
||||
|
||||
say "Done, drop $conf ..."
|
||||
run "rm $conf"
|
||||
run "initctl reload"
|
||||
}
|
||||
|
||||
test_one()
|
||||
{
|
||||
pre=$1
|
||||
@@ -23,31 +88,15 @@ test_one()
|
||||
service=$3
|
||||
post=$4
|
||||
postcont=$5
|
||||
avail="$FINIT_RCSD/available/serv.conf"
|
||||
|
||||
say "Add service stanza '$service' to $FINIT_CONF ..."
|
||||
run "echo '$service' > $FINIT_CONF"
|
||||
sep "Stage 1/2"
|
||||
startit "$service" "$FINIT_CONF" "$pre" "$precont"
|
||||
stopit "$FINIT_CONF" "$post" "$postcont"
|
||||
|
||||
say 'Reload Finit'
|
||||
run "initctl reload"
|
||||
|
||||
retry 'assert_num_children 1 serv'
|
||||
if [ -n "$pre" ]; then
|
||||
assert_file_contains "$pre" "$precont"
|
||||
run "rm -f $pre"
|
||||
fi
|
||||
|
||||
say 'Stop the service'
|
||||
run "initctl stop serv"
|
||||
|
||||
retry 'assert_num_children 0 serv'
|
||||
if [ -n "$post" ]; then
|
||||
assert_file_contains "$post" "$postcont"
|
||||
run "rm -f $post"
|
||||
fi
|
||||
|
||||
say "Done, drop service from $FINIT_CONF ..."
|
||||
run "rm $FINIT_CONF"
|
||||
run "initctl reload"
|
||||
sep "Stage 2/2"
|
||||
startit "$service" "$avail" "$pre" "$precont"
|
||||
stopit "$avail" "$post" "$postcont"
|
||||
}
|
||||
|
||||
# shellcheck source=/dev/null
|
||||
|
||||
Executable
+66
@@ -0,0 +1,66 @@
|
||||
#!/bin/sh
|
||||
# Regression test for issue #392
|
||||
|
||||
set -eu
|
||||
#set -x
|
||||
|
||||
TEST_DIR=$(dirname "$0")
|
||||
|
||||
test_setup()
|
||||
{
|
||||
say "Test start $(date)"
|
||||
run "mkdir -p /etc/default"
|
||||
}
|
||||
|
||||
test_teardown()
|
||||
{
|
||||
say "Test done $(date)"
|
||||
say "Running test teardown."
|
||||
|
||||
run "rm -f $FINIT_CONF"
|
||||
}
|
||||
|
||||
srv()
|
||||
{
|
||||
say "Adding service $(echo "$1" | sed -n -e 's/^.*-- //p')"
|
||||
run "echo '$1' >> $FINIT_CONF"
|
||||
}
|
||||
|
||||
# shellcheck source=/dev/null
|
||||
. "$TEST_DIR/lib/setup.sh"
|
||||
|
||||
#run "initctl debug"
|
||||
|
||||
# Test systemd notify
|
||||
srv 'service name:test1_systemd [2345] notify:systemd restart:0 serv -i test1 -n -- Systemd proc'
|
||||
srv 'service name:test2 [2345] <service/test1_systemd/ready> serv -i test2 -np -- Dependency test 1'
|
||||
|
||||
# Test pid notify
|
||||
srv "service name:test3_pid [2345] notify:pid <service/test1_systemd/ready> serv -i test3 -np -- Dependency test 2"
|
||||
srv "service name:test4 [2345] <service/test3_pid/ready> serv -i test4 -np -- Dependency test 3"
|
||||
|
||||
sep "$FINIT_CONF"
|
||||
run "cat $FINIT_CONF"
|
||||
sep
|
||||
|
||||
say 'Reload Finit'
|
||||
run "initctl reload"
|
||||
|
||||
say "Waiting for all services to start"
|
||||
retry 'assert_status "test4" "running"' 5 1
|
||||
|
||||
# Load bearing debug. Without this the bug cannot be reproduced!
|
||||
run "initctl debug"
|
||||
|
||||
sep
|
||||
say "Stopping root service, all others should also stop"
|
||||
run "initctl stop test1_systemd"
|
||||
retry 'assert_status "test3_pid" "waiting"' 5 1
|
||||
|
||||
sep
|
||||
say "Verify test4 does not restart"
|
||||
run "initctl status"
|
||||
run "initctl cond dump"
|
||||
assert_status "test4" "waiting"
|
||||
|
||||
return 0
|
||||
@@ -1,5 +1,6 @@
|
||||
#!/bin/sh
|
||||
# Regression test for basic /etc/rc.local functionality
|
||||
# shellcheck disable=SC2317
|
||||
set -eu
|
||||
|
||||
TEST_DIR=$(dirname "$0")
|
||||
|
||||
+8
-4
@@ -19,9 +19,10 @@ test_teardown()
|
||||
|
||||
test_one()
|
||||
{
|
||||
service=$1
|
||||
service=$(echo "$1" | tr -s " ")
|
||||
file=/tmp/ready
|
||||
|
||||
sep
|
||||
say "Add service stanza '$service' to $FINIT_CONF ..."
|
||||
run "echo '$service' > $FINIT_CONF"
|
||||
|
||||
@@ -29,6 +30,9 @@ test_one()
|
||||
run "initctl reload"
|
||||
|
||||
retry 'assert_num_children 1 serv'
|
||||
retry 'assert_ready "serv"' 5 1
|
||||
# run "initctl status"
|
||||
# run "initctl cond dump"
|
||||
assert_file_contains "$file" "READY"
|
||||
run "rm -f $file"
|
||||
|
||||
@@ -46,6 +50,6 @@ test_one()
|
||||
|
||||
#run "initctl debug"
|
||||
|
||||
test_one "service ready:/bin/ready.sh serv -np -- Native style notification"
|
||||
test_one "service notify:s6 ready:/bin/ready.sh serv -np -N %n -- s6 style notification"
|
||||
test_one "service notify:systemd ready:/bin/ready.sh serv -np -- systemd style notification"
|
||||
test_one "service ready:/bin/ready.sh serv -np -- Native PID style notification"
|
||||
test_one "service notify:s6 ready:/bin/ready.sh serv -n -N %n -- s6 style notification"
|
||||
test_one "service notify:systemd ready:/bin/ready.sh serv -n -- systemd style notification"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
#!/bin/sh
|
||||
# Regression test for issue #351 - verify that a dirty run/task in
|
||||
# runlevel S is not restarted forever jus because it exits with a
|
||||
# runlevel S is not restarted forever just because it exits with a
|
||||
# non-zero error code.
|
||||
set -eu
|
||||
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user