s6
Software
skarnet.org
How do I perform socket activation with s6 ?
First, it's important to realize that you don't need
socket activation. It's a marketing word used by systemd
advocates that mixes a couple useful architecture concepts and several
horrible ideas, for a very minor speed benefit. Read
this mail
and
this
post for details.
- s6 will not help you implement super-servers in process 1,
because doing so is bad engineering.
However, it will help you set up super-servers. The
s6-ipcserver
program, for Unix domain sockets, as well as the
s6-tcpserver4 and
s6-tcpserver6
programs, for TCP INET domain sockets (available in the
s6-networking
package) are super-servers you can use to
your heart's content. They are even wrappers around simpler programs,
and you can use their components in the way you choose: bind sockets,
drop privileges, accept connections from clients, it's all about what you
write in your command line. Super-servers are a good thing; using process 1
to act as a super-server is not. s6 provides you with the tools to get
the good without the bad.
- s6 will not help you run all your services before their
dependencies are met, because doing so is very bad engineering.
However, it will provide you with:
- s6 will not help you centralize all your socket information
in process 1, because doing so is contrary to modularity and independence
of services. However, s6
will provide you with a way to store your open sockets and
retrieve them when you want, which it calls "fd holding":
s6-fdholder-daemon.
So, how do I open all my sockets first, store them, and dispatch them
to daemons later ?
Again, it's not necessary to do that: you'll be fine, and quite speedy,
just starting your
daemons in their good time. You will not reap any noticeable
benefit from performing "socket activation". But if you really want to:
- Make sure you have an early supervision infrastructure running.
Ideally, you would make s6-svscan your
process 1.
- Start an early fd-holding
service. Let's say the fd-holding daemon is listening on socket
/service/fdholder/s.
- For every Unix domain socket /my/socket you need to open, run
s6-ipcserver-socketbinder /my/socket s6-fdholder-store /service/fdholder/s
unix:/my/socket. You can do the same with INET domain sockets.
- Proceed to your initialization.
- When you want to run a daemon myserverd that accepts clients
connecting to /my/socket, run s6-fdholder-retrieve
/service/fdholder/s unix:/my/socket myserverd. myserverd
will be executed with /my/socket as its standard input.
- The descriptors remain safely stored in the fd-holding daemon and you
can retrieve them again whenever you want, for instance when your service
crashes and is restarted.
That is all there is to it. You don't have to use specific libraries
or write complex unit files, you just need to understand how a command
line works. This is Unix.