Posted at

sd_notifyの通信方法

More than 5 years have passed since last update.

systemdのマネージャ(デーモンプロセス)は、起動プロセスの最後の方でsd_notifyという関数を用いて、起動が完了したことをsystemd本体(PID=1)に通知する。(注:sd_notifyは実際にはもっと汎用的なステータス通知に使える。)

マネージャとsystemdとの通信方法には、抽象名前空間を用いるUnixドメインソケットが使用される。このソケットは、unix(7)にある通り、ファイルシステムを用いないLinux独自のUnixドメインソケットのことである。ファイルパスの先頭を\0にすることで作成できる。

systemdはsd_notifyのために/org/freedesktop/systemd1/notifyという名前のソケットを作成する。マネージャにはNOTIFY_SOCKETという環境変数を通して、この名前を伝える。

systemdが動いているマシン上でnetstat --protocol=unix |grep systemdなどとするとソケットが確認できるはずである。

$ netstat --protocol=unix |grep systemd

unix 2 [ ] DGRAM 8979 /run/systemd/shutdownd
unix 2 [ ] DGRAM 35790 @/org/freedesktop/systemd1/notify
unix 5 [ ] DGRAM 1197 /run/systemd/journal/socket
unix 2 [ ] DGRAM 8939 /run/systemd/journal/syslog
unix 3 [ ] STREAM CONNECTED 13547 /run/systemd/journal/stdout
unix 3 [ ] STREAM CONNECTED 13553 /run/systemd/journal/stdout
unix 3 [ ] STREAM CONNECTED 12938 /run/systemd/journal/stdout
unix 3 [ ] STREAM CONNECTED 13555 /run/systemd/journal/stdout
unix 3 [ ] STREAM CONNECTED 13591 /run/systemd/journal/stdout
unix 3 [ ] STREAM CONNECTED 13554 /run/systemd/journal/stdout
unix 3 [ ] STREAM CONNECTED 13999 /run/systemd/journal/stdout
unix 3 [ ] STREAM CONNECTED 13565 /run/systemd/journal/stdout

また適当なマネージャの環境変数を見てみるとNOTIFY_SOCKETが設定されているのが分かる。

$ sudo cat /proc/$(pidof systemd-journald)/environ |tr -s '\0' '\n'

BOOT_IMAGE=/vmlinuz-3.14.17-100.fc19.x86_64
LANG=en_US.UTF-8
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin
NOTIFY_SOCKET=@/org/freedesktop/systemd1/notify
LISTEN_PID=170
LISTEN_FDS=3