From bb2d7becfd3008379f8f69b5d036922281aa211f Mon Sep 17 00:00:00 2001 From: William Hubbs Date: Mon, 11 May 2015 18:07:28 -0500 Subject: [PATCH] Add support for the s6 supervision suite --- init.d/Makefile | 2 +- init.d/s6-svscan.in | 31 +++++++++++++++++++++++++ man/openrc-run.8 | 12 ++++++++++ s6-guide.md | 56 +++++++++++++++++++++++++++++++++++++++++++++ sh/Makefile | 2 +- sh/openrc-run.sh.in | 4 ++++ sh/s6.sh | 46 +++++++++++++++++++++++++++++++++++++ 7 files changed, 151 insertions(+), 2 deletions(-) create mode 100644 init.d/s6-svscan.in create mode 100644 s6-guide.md create mode 100644 sh/s6.sh diff --git a/init.d/Makefile b/init.d/Makefile index 0bd3651b..a662f8d7 100644 --- a/init.d/Makefile +++ b/init.d/Makefile @@ -3,7 +3,7 @@ include ../mk/net.mk DIR= ${INITDIR} SRCS= bootmisc.in fsck.in hostname.in local.in localmount.in loopback.in \ netmount.in osclock.in root.in savecache.in swap.in swapfiles.in \ - tmpfiles.setup.in swclock.in sysctl.in urandom.in ${SRCS-${OS}} + tmpfiles.setup.in swclock.in sysctl.in urandom.in s6-svscan.in ${SRCS-${OS}} BIN= ${OBJS} # Are we installing our network scripts? diff --git a/init.d/s6-svscan.in b/init.d/s6-svscan.in new file mode 100644 index 00000000..6fdf4e1d --- /dev/null +++ b/init.d/s6-svscan.in @@ -0,0 +1,31 @@ +#!@SBINDIR@/openrc-run +# Copyright (C) 2015 William Hubbs +# Released under the 2-clause BSD license. + +command=/bin/s6-svscan +command_args="${RC_SVCDIR}"/s6-scan +command_background=yes +pidfile=/var/run/s6-svscan.pid + +depend() +{ + need localmount +} + +start_pre() +{ + einfo "Creating s6 scan directory" + checkpath -d -m 0755 "$RC_SVCDIR"/s6-scan + return $? +} + +stop_post() +{ + ebegin "Stopping any remaining s6 services" + s6-svc -dx "${RC_SVCDIR}"/s6-scan/* 2>/dev/null || true + eend $? + + ebegin "Stopping any remaining s6 service loggers" + s6-svc -dx "${RC_SVCDIR}"/s6-scan/*/log 2>/dev/null || true + eend $? +} diff --git a/man/openrc-run.8 b/man/openrc-run.8 index f1441525..259d23fc 100644 --- a/man/openrc-run.8 +++ b/man/openrc-run.8 @@ -107,6 +107,18 @@ the service has already been stopped. String describing the service. .It Ar description_$command String describing the extra command. +.It Ar supervisor +Supervisor to use to monitor this daemon. If this is unset, +start-stop-daemon will be used. The only alternate supervisor we support +in this release is S6 from Skarnet software. To use this, set +supervisor=s6. +.It Ar s6_service_path +The path to the s6 service directory if you are monitoring this service +with S6. The default is /etc/svc.d/${RC_SVCNAME}. +.It Ar s6_svwait_options_start +The options to pass to s6-svwait when starting the service via s6. +.It Ar s6_svwait_options_stop +The options to pass to s6-svwait when stopping the service via s6. .It Ar start_stop_daemon_args List of arguments passed to start-stop-daemon when starting the daemon. .It Ar command diff --git a/s6-guide.md b/s6-guide.md new file mode 100644 index 00000000..4a37a9cc --- /dev/null +++ b/s6-guide.md @@ -0,0 +1,56 @@ +# Using S6 with OpenRC + +Beginning with OpenRC-0.16, we support using the s6 supervision suite +from Skarmet Software in place of start-stop-daemon for monitoring +daemons [1]. + +## Setup + +Documenting s6 in detail is beyond the scope of this guide. It will +document how to set up OpenRC services to communicate with s6. + +### Use Default start, stop and status functions + +If you write your own start, stop and status functions in your service +script, none of this will work. You must allow OpenRC to use the default +functions. + +### Dependencies + +All OpenRC service scripts that want their daemons monitored by s6 +should have the following line added to their dependencies to make sure +the s6 scan directory is being monitored. + +need s6-svscan + +### Variable Settings + +The most important setting is the supervisor variable. At the top of +your service script, you should set this variable as follows: + +supervisor=s6 + +Several other variables affect s6 services. They are documented on the +openrc-run man page, but I will list them here for convenience: + +s6_service_path - the path to the s6 service directory +s6_svwait_options_start - the options to pass to s6-svwait when starting +s6_svwait_options_stop - the options to pass to s6-svwait when stopping. + +The s6_service_path variable defaults to /etc/svc.d/${RC_SVCNAME} if it +is not set in the service script. For example, if you want a service +script called /etc/init.d/foobar to use s6 to monitor its daemon, the s6 +service should be the directory /etc/svc.d/foobar. + +See the documentation for s6 for more information about s6 service +directories. + +The s6_svwait_options_* variables set command line options to pass to +s6-svwait when starting or stopping the s6 service. These can be very +useful for waiting for s6 services to signal when they are up, timing out +when an s6 service doesn't come up, etc. + +This is very early support, so feel free to file bugs if you have +issues. + +[1] https://www.skarnet.org/software/s6 diff --git a/sh/Makefile b/sh/Makefile index 3f8881e8..b9b9fb33 100644 --- a/sh/Makefile +++ b/sh/Makefile @@ -1,7 +1,7 @@ DIR= ${LIBEXECDIR}/sh SRCS= init.sh.in functions.sh.in gendepends.sh.in \ openrc-run.sh.in rc-functions.sh.in tmpfiles.sh.in ${SRCS-${OS}} -INC= rc-mount.sh functions.sh rc-functions.sh start-stop-daemon.sh +INC= rc-mount.sh functions.sh rc-functions.sh s6.sh start-stop-daemon.sh BIN= gendepends.sh init.sh openrc-run.sh tmpfiles.sh ${BIN-${OS}} INSTALLAFTER= _installafter diff --git a/sh/openrc-run.sh.in b/sh/openrc-run.sh.in index 67e47b75..33dc59c5 100644 --- a/sh/openrc-run.sh.in +++ b/sh/openrc-run.sh.in @@ -132,6 +132,7 @@ start() { local func=ssd_start case "$supervisor" in + s6) func=s6_start ;; ?*) ewarn "Invalid supervisor, \"$supervisor\", using start-stop-daemon" ;; @@ -143,6 +144,7 @@ stop() { local func=ssd_stop case "$supervisor" in + s6) func=s6_stop ;; ?*) ewarn "Invalid supervisor, \"$supervisor\", using start-stop-daemon" ;; @@ -154,6 +156,7 @@ status() { local func=ssd_status case "$supervisor" in + s6) func=s6_status ;; ?*) ewarn "Invalid supervisor, \"$supervisor\", using start-stop-daemon" ;; @@ -183,6 +186,7 @@ unset _conf_d sourcex -e "@SYSCONFDIR@/rc.conf" # load service supervisor functions +sourcex "@LIBEXECDIR@/sh/s6.sh" sourcex "@LIBEXECDIR@/sh/start-stop-daemon.sh" # Set verbose mode diff --git a/sh/s6.sh b/sh/s6.sh new file mode 100644 index 00000000..780beab2 --- /dev/null +++ b/sh/s6.sh @@ -0,0 +1,46 @@ +# Start / stop / status functions for s6 support +# Copyright (c) 2015 William Hubbs +# Released under the 2-clause BSD license. + +[ -z "${s6_service_path}" ] && s6_service_path="/etc/svc.d/${RC_SVCNAME}" + +s6_start() +{ + if [ ! -d "${s6_service_path}" ]; then + eerror "${s6_service_path} does not exist." + return 1 + fi + local rc + ebegin "Starting ${name:-$RC_SVCNAME}" + ln -sf "${s6_service_path}" "${RC_SVCDIR}"/s6-scan + s6-svscanctl -an "${RC_SVCDIR}"/s6-scan + rc=$? + if [ -n "$s6_svwait_options_start" ]; then + s6-svwait ${s6_svwait_options_start} "${s6_service_path}" + rc=$? + fi + eend $rc "Failed to start $RC_SVCNAME" +} + +s6_stop() +{ + if [ ! -d "${s6_service_path}" ]; then + eerror "${s6_service_path} does not exist." + return 1 + fi + local rc + ebegin "Stopping ${name:-$RC_SVCNAME}" + rm -rf "${RC_SVCDIR}/s6-scan/${s6_service_path##*/}" + s6-svscanctl -an "${RC_SVCDIR}"/s6-scan + rc=$? + if [ -n "$s6_svwait_options_stop" ]; then + s6-svwait ${s6_svwait_options_stop} "${s6_service_path}" + rc=$? + fi + eend $rc "Failed to stop $RC_SVCNAME" +} + +s6_status() +{ + s6-svstat "${s6_service_path}" +}