Dear init-system-helpers maintainers,

> Now it's likely that I have to support also a catch-all package for
> runit services in addition to the standard dh-runit code

such support is now done, so I'm attaching an updated patchset:

* no patch is needed for update-rc.d: the rescan need to happen
  between enable and signal to a service; both actions are handled
  by runit-helper, so a rescan in update-rc.d is not useful.

* invoke-rc.d: what is needed is a way to block invoke-rc.d when
  a native runit service is found, so that duplicated and conflicting
  instances are avoided. I've added an override mechanism.

* service: patch updated for new service layout; also --status-all
  is changed so that runscripts status is distinguishable from the
  sysv status (runit currently uses a mix of native and sysv scripts
  so the distinction is useful)

Regards,
Lorenzo
>From f50645c3fa7b04204f6749afa4480a6d59077282 Mon Sep 17 00:00:00 2001
From: Lorenzo Puliti <plore...@disroot.org>
Date: Wed, 28 Aug 2024 00:03:04 +0200
Subject: [PATCH 1/3] Add Depends: runit-helper

so that postrm (purge) code can be called safely.
---
 debian/control | 1 +
 1 file changed, 1 insertion(+)

diff --git a/debian/control b/debian/control
index a804662..c1a5421 100644
--- a/debian/control
+++ b/debian/control
@@ -25,6 +25,7 @@ Multi-Arch: foreign
 Depends: ${misc:Depends},
          ${perl:Depends},
          usrmerge | usr-is-merged,
+         runit-helper,
 Description: helper tools for all init systems
  This package contains helper tools that are necessary for switching between
  the various init systems that Debian contains (e. g. sysvinit or
-- 
2.45.2

>From d889c63ec30b38d31aec973bb6706e1f6d669669 Mon Sep 17 00:00:00 2001
From: Lorenzo Puliti <plore...@disroot.org>
Date: Wed, 28 Aug 2024 00:17:48 +0200
Subject: [PATCH 2/3] invoke-rc.d: add support for runit

add an override for runit so that is possible to avoid duplicate
(sometimes conflicting) instances of services
---
 script/invoke-rc.d | 14 ++++++++++++++
 1 file changed, 14 insertions(+)

diff --git a/script/invoke-rc.d b/script/invoke-rc.d
index ca1bdbe..9294de6 100755
--- a/script/invoke-rc.d
+++ b/script/invoke-rc.d
@@ -39,6 +39,7 @@ RETURNFAILURE=
 RC=
 is_systemd=
 is_openrc=
+is_runit=
 SKIP_SYSTEMD_NATIVE=
 
 # Shell options
@@ -279,6 +280,8 @@ if test -d /run/systemd/system ; then
     UNIT="${INITSCRIPTID%.sh}.service"
 elif test -f /run/openrc/softlevel ; then
     is_openrc=1
+elif test -f /run/runit.stopit ; then
+    is_runit=1
 elif test ! -f "${INITDPREFIX}${INITSCRIPTID}" ; then
     ## Verifies if the given initscript ID is known
     ## For sysvinit, this error is critical
@@ -456,6 +459,17 @@ if test x${MODE} = xquery ; then
     exit ${RC}
 fi
 
+## runit sysv-override: first the sysv policy layer
+## is tested so that runit override does not interfere
+## with installer or other packages that uses policy-rc.d
+if [ ${RC} -eq 104 ];then
+    if [ -n "$is_runit" ] && [ -x /etc/runit/override-sysv.d/runit-default ]; then
+        /etc/runit/override-sysv.d/runit-default "${INITSCRIPTID}" "${ACTION}" "$@"
+        if [ "$?" -ne "104"  ]; then
+            exit 0
+        fi
+    fi
+fi
 
 setechoactions () {
     if test $# -gt 1 ; then
-- 
2.45.2

>From cb71628d9900b9ab69a894f96a589fd6b62afcd2 Mon Sep 17 00:00:00 2001
From: Lorenzo Puliti <plore...@disroot.org>
Date: Wed, 28 Aug 2024 01:04:56 +0200
Subject: [PATCH 3/3] service: add support for runit

exec action on native runit service if it exists, otherwise fallback
on sysv script; sysv 'full-restart' is mapped as sv's 'exit'.
--status-all first shows the status of runit-services, then, for
services where a native runit script is not found, the sysv script
status is printed.
---
 script/service | 62 +++++++++++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 61 insertions(+), 1 deletion(-)

diff --git a/script/service b/script/service
index 08f69bb..623bfd4 100755
--- a/script/service
+++ b/script/service
@@ -49,7 +49,10 @@ ACTION=
 SERVICEDIR="/etc/init.d"
 OPTIONS=
 is_systemd=
-
+is_runit=
+# runit service dirs
+ETCSVDIR="/etc/sv"
+USRSVDIR="/usr/share/runit/sv.current"
 
 if [ $# -eq 0 ]; then
    echo "${USAGE}" >&2
@@ -59,6 +62,9 @@ fi
 if [ -d /run/systemd/system ]; then
    is_systemd=1
 fi
+if [ -f /run/runit.stopit ]; then
+   is_runit=1
+fi
 
 cd /
 while [ $# -gt 0 ]; do
@@ -73,6 +79,29 @@ while [ $# -gt 0 ]; do
        ;;
     *)
        if [ -z "${SERVICE}" -a $# -eq 1 -a "${1}" = "--status-all" ]; then
+          if [ -n "$is_runit" ]; then
+            printf "=== Native runit services ===\n"
+            sv s /etc/service/*
+            cd "$ETCSVDIR"
+            for SVS in * ; do
+                if [ -h /etc/service/"${SVS}" ]; then
+                    continue # skip: already done
+                else
+                    echo "disabled: ${SVS}"
+                fi
+            done
+            cd "$USRSVDIR"
+            for SVS in * ; do
+                if [ -d "$ETCSVDIR"/"${SVS}" ]; then
+                    continue # skip: superseded by local service in /etc/sv
+                elif [ -h /etc/service/"${SVS}" ]; then
+                    continue # skip: already done
+                else
+                    echo "disabled: ${SVS}"
+                fi
+            done
+            printf "=== Sysv services ===\n"
+          fi
           cd ${SERVICEDIR}
           for SERVICE in * ; do
             case "${SERVICE}" in
@@ -81,6 +110,14 @@ while [ $# -gt 0 ]; do
               *)
                 if ! is_ignored_file "${SERVICE}" \
 		    && [ -x "${SERVICEDIR}/${SERVICE}" ]; then
+                        if [ -n "$is_runit" ]; then
+                           if [ -h /etc/service/"${SERVICE}" ] || [ -e /etc/service/."${SERVICE}" ]; then
+                              continue # skip: native runit service enabled or disabled
+                           fi
+                           if [ -d "$ETCSVDIR"/"${SERVICE}" ] || [ -d "$USRSVDIR"/"${SERVICE}" ]; then
+                              continue # skip: native runit service definition exists, not enabled
+                           fi
+                        fi
                         out=$(env -i LANG="$LANG" LANGUAGE="$LANGUAGE" LC_CTYPE="$LC_CTYPE" LC_NUMERIC="$LC_NUMERIC" LC_TIME="$LC_TIME" LC_COLLATE="$LC_COLLATE" LC_MONETARY="$LC_MONETARY" LC_MESSAGES="$LC_MESSAGES" LC_PAPER="$LC_PAPER" LC_NAME="$LC_NAME" LC_ADDRESS="$LC_ADDRESS" LC_TELEPHONE="$LC_TELEPHONE" LC_MEASUREMENT="$LC_MEASUREMENT" LC_IDENTIFICATION="$LC_IDENTIFICATION" LC_ALL="$LC_ALL" PATH="$PATH" TERM="$TERM" "$SERVICEDIR/$SERVICE" status 2>&1)
                         retval=$?
                         if echo "$out" | grep -Fiq "usage:"; then
@@ -110,6 +147,10 @@ while [ $# -gt 0 ]; do
           # A restart with systemd is already a full restart.
           if [ -n "$is_systemd" ]; then
              ACTION="restart"
+          # full-restart mapped as exit in runit: exit will stop the service, the stop the
+          # log (if any) and stop the runsv monitor; then it will be restarted
+          elif [ -n "$is_runit" ]; then
+             ACTION="exit"
           else
              if [ -x "${SERVICEDIR}/${SERVICE}" ]; then
                env -i LANG="$LANG" LANGUAGE="$LANGUAGE" LC_CTYPE="$LC_CTYPE" LC_NUMERIC="$LC_NUMERIC" LC_TIME="$LC_TIME" LC_COLLATE="$LC_COLLATE" LC_MONETARY="$LC_MONETARY" LC_MESSAGES="$LC_MESSAGES" LC_PAPER="$LC_PAPER" LC_NAME="$LC_NAME" LC_ADDRESS="$LC_ADDRESS" LC_TELEPHONE="$LC_TELEPHONE" LC_MEASUREMENT="$LC_MEASUREMENT" LC_IDENTIFICATION="$LC_IDENTIFICATION" LC_ALL="$LC_ALL" PATH="$PATH" TERM="$TERM" "$SERVICEDIR/$SERVICE" stop
@@ -213,5 +254,24 @@ then
    esac
 fi
 
+if [ -n "$is_runit" ]; then
+   if [ ! -h /etc/service/"${SERVICE}" ] || [ -e /etc/service/."${SERVICE}" ]; then
+      if [ -d "$ETCSVDIR/${SERVICE}" ] || [ -d "$USRSVDIR/${SERVICE}"  ]; then
+           exec printf  "${SERVICE}: disabled\n"
+      fi
+   fi
+   if [ -h /etc/service/"${SERVICE}" ]; then
+      case "${ACTION}" in
+         start|stop|restart|reload|status|try-restart|force-stop|force-reload|exit)
+            exec sv "${ACTION}" "${SERVICE}"
+         ;;
+         *)
+            echo "error: ${ACTION} not supported by sv"
+            exec sv "${ACTION}" "${SERVICE}" # will print usage and exit 100
+         ;;
+      esac
+   fi
+fi
+
 update_openrc_started_symlinks
 run_via_sysvinit
-- 
2.45.2

Reply via email to