about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--package/deps.mak13
-rw-r--r--src/daemontools-extras/s6-log.c11
-rw-r--r--src/daemontools-extras/s6-setlock.c18
-rw-r--r--src/libs6/deps-lib/s64
-rw-r--r--src/libs6/s6_supervise_lock.c9
-rw-r--r--src/libs6/s6_supervise_lock_mode.c85
-rw-r--r--src/libs6/s6_svc_lock_release.c8
-rw-r--r--src/libs6/s6_svc_lock_take.c28
-rw-r--r--src/libs6/s6_svc_ok.c23
-rw-r--r--src/libs6/s6lockd-helper.c17
-rw-r--r--src/libs6/s6lockd.c10
-rw-r--r--src/supervision/deps-exe/s6-svscan1
-rw-r--r--src/supervision/s6-supervise.c95
-rw-r--r--src/supervision/s6-svscan.c47
14 files changed, 181 insertions, 188 deletions
diff --git a/package/deps.mak b/package/deps.mak
index 9d050fa..08b7aec 100644
--- a/package/deps.mak
+++ b/package/deps.mak
@@ -90,10 +90,7 @@ src/libs6/s6_fdholder_setdump.o src/libs6/s6_fdholder_setdump.lo: src/libs6/s6_f
 src/libs6/s6_fdholder_start.o src/libs6/s6_fdholder_start.lo: src/libs6/s6_fdholder_start.c src/include/s6/s6-fdholder.h
 src/libs6/s6_fdholder_store.o src/libs6/s6_fdholder_store.lo: src/libs6/s6_fdholder_store.c src/include/s6/s6-fdholder.h
 src/libs6/s6_fdholder_store_async.o src/libs6/s6_fdholder_store_async.lo: src/libs6/s6_fdholder_store_async.c src/include/s6/s6-fdholder.h
-src/libs6/s6_supervise_lock.o src/libs6/s6_supervise_lock.lo: src/libs6/s6_supervise_lock.c src/include/s6/s6-supervise.h
-src/libs6/s6_supervise_lock_mode.o src/libs6/s6_supervise_lock_mode.lo: src/libs6/s6_supervise_lock_mode.c src/include/s6/s6-supervise.h
-src/libs6/s6_svc_lock_release.o src/libs6/s6_svc_lock_release.lo: src/libs6/s6_svc_lock_release.c
-src/libs6/s6_svc_lock_take.o src/libs6/s6_svc_lock_take.lo: src/libs6/s6_svc_lock_take.c src/include/s6/s6-supervise.h
+src/libs6/s6_supervise_link.o src/libs6/s6_supervise_link.lo: src/libs6/s6_supervise_link.c src/include/s6/ftrigr.h src/include/s6/s6-supervise.h
 src/libs6/s6_svc_ok.o src/libs6/s6_svc_ok.lo: src/libs6/s6_svc_ok.c src/include/s6/s6-supervise.h
 src/libs6/s6_svc_write.o src/libs6/s6_svc_write.lo: src/libs6/s6_svc_write.c src/include/s6/s6-supervise.h
 src/libs6/s6_svc_writectl.o src/libs6/s6_svc_writectl.lo: src/libs6/s6_svc_writectl.c src/include/s6/s6-supervise.h
@@ -202,12 +199,12 @@ s6-fdholder-transferdump: src/fdholder/s6-fdholder-transferdump.o ${LIBS6}
 s6-fdholderd: EXTRA_LIBS := -lskarnet ${SOCKET_LIB} ${SYSCLOCK_LIB}
 s6-fdholderd: src/fdholder/s6-fdholderd.o ${LIBS6}
 ifeq ($(strip $(STATIC_LIBS_ARE_PIC)),)
-libs6.a.xyzzy: src/libs6/ftrigr1_zero.o src/libs6/ftrigr_check.o src/libs6/ftrigr_checksa.o src/libs6/ftrigr_ack.o src/libs6/ftrigr_end.o src/libs6/ftrigr_start.o src/libs6/ftrigr_startf.o src/libs6/ftrigr_subscribe.o src/libs6/ftrigr_unsubscribe.o src/libs6/ftrigr_update.o src/libs6/ftrigr_updateb.o src/libs6/ftrigr_wait_and.o src/libs6/ftrigr_wait_or.o src/libs6/ftrigr_zero.o src/libs6/ftrigw_clean.o src/libs6/ftrigw_fifodir_make.o src/libs6/ftrigw_notify.o src/libs6/ftrigw_notifyb.o src/libs6/ftrigw_notifyb_nosig.o src/libs6/s6_accessrules_backend_cdb.o src/libs6/s6_accessrules_backend_fs.o src/libs6/s6_accessrules_keycheck_ip4.o src/libs6/s6_accessrules_keycheck_ip6.o src/libs6/s6_accessrules_keycheck_reversedns.o src/libs6/s6_accessrules_keycheck_uidgid.o src/libs6/s6_accessrules_params_free.o src/libs6/s6_accessrules_uidgid_cdb.o src/libs6/s6_accessrules_uidgid_fs.o src/libs6/s6_compat_el_semicolon.o src/libs6/s6_dtally_pack.o src/libs6/s6_dtally_unpack.o src/libs6/s6_dtally_read.o src/libs6/s6_dtally_write.o src/libs6/s6_supervise_lock.o src/libs6/s6_supervise_lock_mode.o src/libs6/s6_svc_lock_take.o src/libs6/s6_svc_lock_release.o src/libs6/s6_svc_ok.o src/libs6/s6_svc_write.o src/libs6/s6_svc_writectl.o src/libs6/s6_svstatus_pack.o src/libs6/s6_svstatus_read.o src/libs6/s6_svstatus_unpack.o src/libs6/s6_svstatus_write.o src/libs6/s6lock_acquire.o src/libs6/s6lock_check.o src/libs6/s6lock_end.o src/libs6/s6lock_release.o src/libs6/s6lock_start.o src/libs6/s6lock_startf.o src/libs6/s6lock_update.o src/libs6/s6lock_wait_and.o src/libs6/s6lock_wait_or.o src/libs6/s6lock_zero.o src/libs6/s6_fdholder_delete.o src/libs6/s6_fdholder_delete_async.o src/libs6/s6_fdholder_end.o src/libs6/s6_fdholder_getdump.o src/libs6/s6_fdholder_list.o src/libs6/s6_fdholder_list_async.o src/libs6/s6_fdholder_list_cb.o src/libs6/s6_fdholder_retrieve.o src/libs6/s6_fdholder_retrieve_async.o src/libs6/s6_fdholder_retrieve_cb.o src/libs6/s6_fdholder_setdump.o src/libs6/s6_fdholder_start.o src/libs6/s6_fdholder_store.o src/libs6/s6_fdholder_store_async.o
+libs6.a.xyzzy: src/libs6/ftrigr1_zero.o src/libs6/ftrigr_check.o src/libs6/ftrigr_checksa.o src/libs6/ftrigr_ack.o src/libs6/ftrigr_end.o src/libs6/ftrigr_start.o src/libs6/ftrigr_startf.o src/libs6/ftrigr_subscribe.o src/libs6/ftrigr_unsubscribe.o src/libs6/ftrigr_update.o src/libs6/ftrigr_updateb.o src/libs6/ftrigr_wait_and.o src/libs6/ftrigr_wait_or.o src/libs6/ftrigr_zero.o src/libs6/ftrigw_clean.o src/libs6/ftrigw_fifodir_make.o src/libs6/ftrigw_notify.o src/libs6/ftrigw_notifyb.o src/libs6/ftrigw_notifyb_nosig.o src/libs6/s6_accessrules_backend_cdb.o src/libs6/s6_accessrules_backend_fs.o src/libs6/s6_accessrules_keycheck_ip4.o src/libs6/s6_accessrules_keycheck_ip6.o src/libs6/s6_accessrules_keycheck_reversedns.o src/libs6/s6_accessrules_keycheck_uidgid.o src/libs6/s6_accessrules_params_free.o src/libs6/s6_accessrules_uidgid_cdb.o src/libs6/s6_accessrules_uidgid_fs.o src/libs6/s6_compat_el_semicolon.o src/libs6/s6_dtally_pack.o src/libs6/s6_dtally_unpack.o src/libs6/s6_dtally_read.o src/libs6/s6_dtally_write.o src/libs6/s6_svc_ok.o src/libs6/s6_svc_write.o src/libs6/s6_svc_writectl.o src/libs6/s6_svstatus_pack.o src/libs6/s6_svstatus_read.o src/libs6/s6_svstatus_unpack.o src/libs6/s6_svstatus_write.o src/libs6/s6lock_acquire.o src/libs6/s6lock_check.o src/libs6/s6lock_end.o src/libs6/s6lock_release.o src/libs6/s6lock_start.o src/libs6/s6lock_startf.o src/libs6/s6lock_update.o src/libs6/s6lock_wait_and.o src/libs6/s6lock_wait_or.o src/libs6/s6lock_zero.o src/libs6/s6_fdholder_delete.o src/libs6/s6_fdholder_delete_async.o src/libs6/s6_fdholder_end.o src/libs6/s6_fdholder_getdump.o src/libs6/s6_fdholder_list.o src/libs6/s6_fdholder_list_async.o src/libs6/s6_fdholder_list_cb.o src/libs6/s6_fdholder_retrieve.o src/libs6/s6_fdholder_retrieve_async.o src/libs6/s6_fdholder_retrieve_cb.o src/libs6/s6_fdholder_setdump.o src/libs6/s6_fdholder_start.o src/libs6/s6_fdholder_store.o src/libs6/s6_fdholder_store_async.o
 else
-libs6.a.xyzzy: src/libs6/ftrigr1_zero.lo src/libs6/ftrigr_check.lo src/libs6/ftrigr_checksa.lo src/libs6/ftrigr_ack.lo src/libs6/ftrigr_end.lo src/libs6/ftrigr_start.lo src/libs6/ftrigr_startf.lo src/libs6/ftrigr_subscribe.lo src/libs6/ftrigr_unsubscribe.lo src/libs6/ftrigr_update.lo src/libs6/ftrigr_updateb.lo src/libs6/ftrigr_wait_and.lo src/libs6/ftrigr_wait_or.lo src/libs6/ftrigr_zero.lo src/libs6/ftrigw_clean.lo src/libs6/ftrigw_fifodir_make.lo src/libs6/ftrigw_notify.lo src/libs6/ftrigw_notifyb.lo src/libs6/ftrigw_notifyb_nosig.lo src/libs6/s6_accessrules_backend_cdb.lo src/libs6/s6_accessrules_backend_fs.lo src/libs6/s6_accessrules_keycheck_ip4.lo src/libs6/s6_accessrules_keycheck_ip6.lo src/libs6/s6_accessrules_keycheck_reversedns.lo src/libs6/s6_accessrules_keycheck_uidgid.lo src/libs6/s6_accessrules_params_free.lo src/libs6/s6_accessrules_uidgid_cdb.lo src/libs6/s6_accessrules_uidgid_fs.lo src/libs6/s6_compat_el_semicolon.lo src/libs6/s6_dtally_pack.lo src/libs6/s6_dtally_unpack.lo src/libs6/s6_dtally_read.lo src/libs6/s6_dtally_write.lo src/libs6/s6_supervise_lock.lo src/libs6/s6_supervise_lock_mode.lo src/libs6/s6_svc_lock_take.lo src/libs6/s6_svc_lock_release.lo src/libs6/s6_svc_ok.lo src/libs6/s6_svc_write.lo src/libs6/s6_svc_writectl.lo src/libs6/s6_svstatus_pack.lo src/libs6/s6_svstatus_read.lo src/libs6/s6_svstatus_unpack.lo src/libs6/s6_svstatus_write.lo src/libs6/s6lock_acquire.lo src/libs6/s6lock_check.lo src/libs6/s6lock_end.lo src/libs6/s6lock_release.lo src/libs6/s6lock_start.lo src/libs6/s6lock_startf.lo src/libs6/s6lock_update.lo src/libs6/s6lock_wait_and.lo src/libs6/s6lock_wait_or.lo src/libs6/s6lock_zero.lo src/libs6/s6_fdholder_delete.lo src/libs6/s6_fdholder_delete_async.lo src/libs6/s6_fdholder_end.lo src/libs6/s6_fdholder_getdump.lo src/libs6/s6_fdholder_list.lo src/libs6/s6_fdholder_list_async.lo src/libs6/s6_fdholder_list_cb.lo src/libs6/s6_fdholder_retrieve.lo src/libs6/s6_fdholder_retrieve_async.lo src/libs6/s6_fdholder_retrieve_cb.lo src/libs6/s6_fdholder_setdump.lo src/libs6/s6_fdholder_start.lo src/libs6/s6_fdholder_store.lo src/libs6/s6_fdholder_store_async.lo
+libs6.a.xyzzy: src/libs6/ftrigr1_zero.lo src/libs6/ftrigr_check.lo src/libs6/ftrigr_checksa.lo src/libs6/ftrigr_ack.lo src/libs6/ftrigr_end.lo src/libs6/ftrigr_start.lo src/libs6/ftrigr_startf.lo src/libs6/ftrigr_subscribe.lo src/libs6/ftrigr_unsubscribe.lo src/libs6/ftrigr_update.lo src/libs6/ftrigr_updateb.lo src/libs6/ftrigr_wait_and.lo src/libs6/ftrigr_wait_or.lo src/libs6/ftrigr_zero.lo src/libs6/ftrigw_clean.lo src/libs6/ftrigw_fifodir_make.lo src/libs6/ftrigw_notify.lo src/libs6/ftrigw_notifyb.lo src/libs6/ftrigw_notifyb_nosig.lo src/libs6/s6_accessrules_backend_cdb.lo src/libs6/s6_accessrules_backend_fs.lo src/libs6/s6_accessrules_keycheck_ip4.lo src/libs6/s6_accessrules_keycheck_ip6.lo src/libs6/s6_accessrules_keycheck_reversedns.lo src/libs6/s6_accessrules_keycheck_uidgid.lo src/libs6/s6_accessrules_params_free.lo src/libs6/s6_accessrules_uidgid_cdb.lo src/libs6/s6_accessrules_uidgid_fs.lo src/libs6/s6_compat_el_semicolon.lo src/libs6/s6_dtally_pack.lo src/libs6/s6_dtally_unpack.lo src/libs6/s6_dtally_read.lo src/libs6/s6_dtally_write.lo src/libs6/s6_svc_ok.lo src/libs6/s6_svc_write.lo src/libs6/s6_svc_writectl.lo src/libs6/s6_svstatus_pack.lo src/libs6/s6_svstatus_read.lo src/libs6/s6_svstatus_unpack.lo src/libs6/s6_svstatus_write.lo src/libs6/s6lock_acquire.lo src/libs6/s6lock_check.lo src/libs6/s6lock_end.lo src/libs6/s6lock_release.lo src/libs6/s6lock_start.lo src/libs6/s6lock_startf.lo src/libs6/s6lock_update.lo src/libs6/s6lock_wait_and.lo src/libs6/s6lock_wait_or.lo src/libs6/s6lock_zero.lo src/libs6/s6_fdholder_delete.lo src/libs6/s6_fdholder_delete_async.lo src/libs6/s6_fdholder_end.lo src/libs6/s6_fdholder_getdump.lo src/libs6/s6_fdholder_list.lo src/libs6/s6_fdholder_list_async.lo src/libs6/s6_fdholder_list_cb.lo src/libs6/s6_fdholder_retrieve.lo src/libs6/s6_fdholder_retrieve_async.lo src/libs6/s6_fdholder_retrieve_cb.lo src/libs6/s6_fdholder_setdump.lo src/libs6/s6_fdholder_start.lo src/libs6/s6_fdholder_store.lo src/libs6/s6_fdholder_store_async.lo
 endif
 libs6.so.xyzzy: EXTRA_LIBS := -lskarnet
-libs6.so.xyzzy: src/libs6/ftrigr1_zero.lo src/libs6/ftrigr_check.lo src/libs6/ftrigr_checksa.lo src/libs6/ftrigr_ack.lo src/libs6/ftrigr_end.lo src/libs6/ftrigr_start.lo src/libs6/ftrigr_startf.lo src/libs6/ftrigr_subscribe.lo src/libs6/ftrigr_unsubscribe.lo src/libs6/ftrigr_update.lo src/libs6/ftrigr_updateb.lo src/libs6/ftrigr_wait_and.lo src/libs6/ftrigr_wait_or.lo src/libs6/ftrigr_zero.lo src/libs6/ftrigw_clean.lo src/libs6/ftrigw_fifodir_make.lo src/libs6/ftrigw_notify.lo src/libs6/ftrigw_notifyb.lo src/libs6/ftrigw_notifyb_nosig.lo src/libs6/s6_accessrules_backend_cdb.lo src/libs6/s6_accessrules_backend_fs.lo src/libs6/s6_accessrules_keycheck_ip4.lo src/libs6/s6_accessrules_keycheck_ip6.lo src/libs6/s6_accessrules_keycheck_reversedns.lo src/libs6/s6_accessrules_keycheck_uidgid.lo src/libs6/s6_accessrules_params_free.lo src/libs6/s6_accessrules_uidgid_cdb.lo src/libs6/s6_accessrules_uidgid_fs.lo src/libs6/s6_compat_el_semicolon.lo src/libs6/s6_dtally_pack.lo src/libs6/s6_dtally_unpack.lo src/libs6/s6_dtally_read.lo src/libs6/s6_dtally_write.lo src/libs6/s6_supervise_lock.lo src/libs6/s6_supervise_lock_mode.lo src/libs6/s6_svc_lock_take.lo src/libs6/s6_svc_lock_release.lo src/libs6/s6_svc_ok.lo src/libs6/s6_svc_write.lo src/libs6/s6_svc_writectl.lo src/libs6/s6_svstatus_pack.lo src/libs6/s6_svstatus_read.lo src/libs6/s6_svstatus_unpack.lo src/libs6/s6_svstatus_write.lo src/libs6/s6lock_acquire.lo src/libs6/s6lock_check.lo src/libs6/s6lock_end.lo src/libs6/s6lock_release.lo src/libs6/s6lock_start.lo src/libs6/s6lock_startf.lo src/libs6/s6lock_update.lo src/libs6/s6lock_wait_and.lo src/libs6/s6lock_wait_or.lo src/libs6/s6lock_zero.lo src/libs6/s6_fdholder_delete.lo src/libs6/s6_fdholder_delete_async.lo src/libs6/s6_fdholder_end.lo src/libs6/s6_fdholder_getdump.lo src/libs6/s6_fdholder_list.lo src/libs6/s6_fdholder_list_async.lo src/libs6/s6_fdholder_list_cb.lo src/libs6/s6_fdholder_retrieve.lo src/libs6/s6_fdholder_retrieve_async.lo src/libs6/s6_fdholder_retrieve_cb.lo src/libs6/s6_fdholder_setdump.lo src/libs6/s6_fdholder_start.lo src/libs6/s6_fdholder_store.lo src/libs6/s6_fdholder_store_async.lo
+libs6.so.xyzzy: src/libs6/ftrigr1_zero.lo src/libs6/ftrigr_check.lo src/libs6/ftrigr_checksa.lo src/libs6/ftrigr_ack.lo src/libs6/ftrigr_end.lo src/libs6/ftrigr_start.lo src/libs6/ftrigr_startf.lo src/libs6/ftrigr_subscribe.lo src/libs6/ftrigr_unsubscribe.lo src/libs6/ftrigr_update.lo src/libs6/ftrigr_updateb.lo src/libs6/ftrigr_wait_and.lo src/libs6/ftrigr_wait_or.lo src/libs6/ftrigr_zero.lo src/libs6/ftrigw_clean.lo src/libs6/ftrigw_fifodir_make.lo src/libs6/ftrigw_notify.lo src/libs6/ftrigw_notifyb.lo src/libs6/ftrigw_notifyb_nosig.lo src/libs6/s6_accessrules_backend_cdb.lo src/libs6/s6_accessrules_backend_fs.lo src/libs6/s6_accessrules_keycheck_ip4.lo src/libs6/s6_accessrules_keycheck_ip6.lo src/libs6/s6_accessrules_keycheck_reversedns.lo src/libs6/s6_accessrules_keycheck_uidgid.lo src/libs6/s6_accessrules_params_free.lo src/libs6/s6_accessrules_uidgid_cdb.lo src/libs6/s6_accessrules_uidgid_fs.lo src/libs6/s6_compat_el_semicolon.lo src/libs6/s6_dtally_pack.lo src/libs6/s6_dtally_unpack.lo src/libs6/s6_dtally_read.lo src/libs6/s6_dtally_write.lo src/libs6/s6_svc_ok.lo src/libs6/s6_svc_write.lo src/libs6/s6_svc_writectl.lo src/libs6/s6_svstatus_pack.lo src/libs6/s6_svstatus_read.lo src/libs6/s6_svstatus_unpack.lo src/libs6/s6_svstatus_write.lo src/libs6/s6lock_acquire.lo src/libs6/s6lock_check.lo src/libs6/s6lock_end.lo src/libs6/s6lock_release.lo src/libs6/s6lock_start.lo src/libs6/s6lock_startf.lo src/libs6/s6lock_update.lo src/libs6/s6lock_wait_and.lo src/libs6/s6lock_wait_or.lo src/libs6/s6lock_zero.lo src/libs6/s6_fdholder_delete.lo src/libs6/s6_fdholder_delete_async.lo src/libs6/s6_fdholder_end.lo src/libs6/s6_fdholder_getdump.lo src/libs6/s6_fdholder_list.lo src/libs6/s6_fdholder_list_async.lo src/libs6/s6_fdholder_list_cb.lo src/libs6/s6_fdholder_retrieve.lo src/libs6/s6_fdholder_retrieve_async.lo src/libs6/s6_fdholder_retrieve_cb.lo src/libs6/s6_fdholder_setdump.lo src/libs6/s6_fdholder_start.lo src/libs6/s6_fdholder_store.lo src/libs6/s6_fdholder_store_async.lo
 s6-ftrigrd: EXTRA_LIBS := -lskarnet ${SOCKET_LIB} ${SYSCLOCK_LIB}
 s6-ftrigrd: src/libs6/s6-ftrigrd.o src/libs6/ftrig1_free.o src/libs6/ftrig1_make.o
 s6lockd: EXTRA_LIBS := -lskarnet ${SOCKET_LIB} ${SYSCLOCK_LIB} ${SPAWN_LIB}
@@ -245,7 +242,7 @@ s6-svlisten1: src/supervision/s6-svlisten1.o src/supervision/s6_svlisten_signal_
 s6-svok: EXTRA_LIBS := -lskarnet
 s6-svok: src/supervision/s6-svok.o ${LIBS6}
 s6-svscan: EXTRA_LIBS := -lskarnet ${SYSCLOCK_LIB} ${SPAWN_LIB}
-s6-svscan: src/supervision/s6-svscan.o ${LIBS6}
+s6-svscan: src/supervision/s6-svscan.o
 s6-svscanctl: EXTRA_LIBS := -lskarnet
 s6-svscanctl: src/supervision/s6-svscanctl.o ${LIBS6}
 s6-svstat: EXTRA_LIBS := -lskarnet ${SYSCLOCK_LIB}
diff --git a/src/daemontools-extras/s6-log.c b/src/daemontools-extras/s6-log.c
index 2f8438d..5128751 100644
--- a/src/daemontools-extras/s6-log.c
+++ b/src/daemontools-extras/s6-log.c
@@ -580,13 +580,14 @@ static inline void logdir_init (unsigned int index, uint32_t s, uint32_t n, uint
   ldp->fd = -1 ;
   ldp->rstate = ROTSTATE_WRITABLE ;
   r = mkdir(ldp->dir, S_IRWXU | S_ISGID) ;
-  if ((r < 0) && (errno != EEXIST)) strerr_diefu2sys(111, "mkdir ", name) ;
+  if (r < 0 && errno != EEXIST) strerr_diefu2sys(111, "mkdir ", name) ;
   memcpy(x, name, dirlen) ;
   memcpy(x + dirlen, "/lock", 6) ;
-  ldp->fdlock = open_append(x) ;
-  if ((ldp->fdlock) < 0) strerr_diefu2sys(111, "open_append ", x) ;
-  if (lock_exnb(ldp->fdlock) < 0) strerr_diefu2sys(111, "lock_exnb ", x) ;
-  if (coe(ldp->fdlock) < 0) strerr_diefu2sys(111, "coe ", x) ;
+  ldp->fdlock = openc_create(x) ;
+  if (ldp->fdlock < 0) strerr_diefu2sys(111, "open ", x) ;
+  r = fd_lock(ldp->fdlock, 1, 1) ;
+  if (!r) errno = EBUSY ;
+  if (r < 1) strerr_diefu2sys(111, "lock ", x) ;
   memcpy(x + dirlen + 1, "current", 8) ;
   if (stat(x, &st) < 0)
   {
diff --git a/src/daemontools-extras/s6-setlock.c b/src/daemontools-extras/s6-setlock.c
index bc50519..cd938b7 100644
--- a/src/daemontools-extras/s6-setlock.c
+++ b/src/daemontools-extras/s6-setlock.c
@@ -18,11 +18,6 @@
 #define USAGE "s6-setlock [ -r | -w ] [ -n | -N | -t timeout ] lockfile prog..."
 #define dieusage() strerr_dieusage(100, USAGE)
 
-typedef int lockfunc_t (int) ;
-typedef lockfunc_t *lockfunc_t_ref ;
-
-static lockfunc_t_ref f[2][2] = { { &lock_sh, &lock_shnb }, { &lock_ex, &lock_exnb } } ;
-
 int main (int argc, char const *const *argv)
 {
   unsigned int nb = 0, ex = 1 ;
@@ -47,14 +42,17 @@ int main (int argc, char const *const *argv)
 
   if (nb < 2)
   {
+    int r ;
     int fd = open_create(argv[0]) ;
-    if (fd == -1) strerr_diefu2sys(111, "open_create ", argv[0]) ;
-    if ((*f[ex][nb])(fd) == -1) strerr_diefu2sys(1, "lock ", argv[0]) ;
+    if (fd < 0) strerr_diefu2sys(111, "open_create ", argv[0]) ;
+    r = fd_lock(fd, ex, nb) ;
+    if (!r) errno = EBUSY ;
+    if (r < 1) strerr_diefu2sys(1, "lock ", argv[0]) ;
   }
   else
   {
-    char const *cargv[3] = { "s6lockd-helper", argv[0], 0 } ;
-    char const *cenvp[2] = { ex ? "S6LOCK_EX=1" : 0, 0 } ;
+    char const *cargv[4] = { "s6lockd-helper", ex ? "w" : "r", argv[0], 0 } ;
+    char const *nullenv = { 0 } ;
     iopause_fd x = { .events = IOPAUSE_READ } ;
     tain_t deadline ;
     int p[2] = { 0, 1 } ;
@@ -63,7 +61,7 @@ int main (int argc, char const *const *argv)
     tain_now_set_stopwatch_g() ;
     tain_from_millisecs(&deadline, timeout) ;
     tain_add_g(&deadline, &deadline) ;
-    pid = child_spawn2(S6_LIBEXECPREFIX "s6lockd-helper", cargv, cenvp, p) ;
+    pid = child_spawn2(S6_LIBEXECPREFIX "s6lockd-helper", cargv, &nullenv, p) ;
     if (!pid) strerr_diefu2sys(111, "spawn ", S6_LIBEXECPREFIX "s6lockd-helper") ;
     x.fd = p[0] ;
     for (;;)
diff --git a/src/libs6/deps-lib/s6 b/src/libs6/deps-lib/s6
index ddd86dc..d9d4341 100644
--- a/src/libs6/deps-lib/s6
+++ b/src/libs6/deps-lib/s6
@@ -31,10 +31,6 @@ s6_dtally_pack.o
 s6_dtally_unpack.o
 s6_dtally_read.o
 s6_dtally_write.o
-s6_supervise_lock.o
-s6_supervise_lock_mode.o
-s6_svc_lock_take.o
-s6_svc_lock_release.o
 s6_svc_ok.o
 s6_svc_write.o
 s6_svc_writectl.o
diff --git a/src/libs6/s6_supervise_lock.c b/src/libs6/s6_supervise_lock.c
deleted file mode 100644
index e241320..0000000
--- a/src/libs6/s6_supervise_lock.c
+++ /dev/null
@@ -1,9 +0,0 @@
-/* ISC license. */
-
-#include <sys/stat.h>
-#include <s6/s6-supervise.h>
-
-int s6_supervise_lock (char const *subdir)
-{
-  return s6_supervise_lock_mode(subdir, S_IRWXU, S_IRUSR | S_IWUSR) ;
-}
diff --git a/src/libs6/s6_supervise_lock_mode.c b/src/libs6/s6_supervise_lock_mode.c
deleted file mode 100644
index d807bec..0000000
--- a/src/libs6/s6_supervise_lock_mode.c
+++ /dev/null
@@ -1,85 +0,0 @@
-/* ISC license. */
-
-#include <limits.h>
-#include <unistd.h>
-#include <sys/stat.h>
-#include <string.h>
-#include <errno.h>
-
-#include <skalibs/strerr2.h>
-#include <skalibs/djbunix.h>
-
-#include <s6/s6-supervise.h>
-
-#ifdef PATH_MAX
-# define S6_PATH_MAX PATH_MAX
-#else
-# define S6_PATH_MAX 4096
-#endif
-
-int s6_supervise_lock_mode (char const *subdir, unsigned int subdirmode, unsigned int controlmode)
-{
-  size_t subdirlen = strlen(subdir) ;
-  int fdctl, fdctlw, fdlock ;
-  char control[subdirlen + 9] ;
-  char lock[subdirlen + 6] ;
-  memcpy(control, subdir, subdirlen) ;
-  memcpy(control + subdirlen, "/control", 9) ;
-  memcpy(lock, subdir, subdirlen) ;
-  memcpy(lock + subdirlen, "/lock", 6) ;
-  if (mkdir(subdir, (mode_t)subdirmode) == -1)
-  {
-    char buf[S6_PATH_MAX] ;
-    ssize_t r ;
-    if (errno == EEXIST) strerr_diefu2sys(111, "mkdir ", subdir) ;
-    r = readlink(subdir, buf, S6_PATH_MAX) ;
-    if (r < 0)
-    {
-      if (errno != EINVAL)
-      {
-        errno = EEXIST ;
-        strerr_diefu2sys(111, "mkdir ", subdir) ;
-      }
-    }
-    else if (r == S6_PATH_MAX)
-    {
-      errno = ENAMETOOLONG ;
-      strerr_diefu2sys(111, "readlink ", subdir) ;
-    }
-    else
-    {
-      buf[r] = 0 ;
-      if (mkdir(buf, (mode_t)subdirmode) == -1)
-        strerr_diefu2sys(111, "mkdir ", buf) ;
-    }
-  }
-  if (mkfifo(control, controlmode) < 0)
-  {
-    struct stat st ;
-    if (errno != EEXIST)
-      strerr_diefu2sys(111, "mkfifo ", control) ;
-    if (stat(control, &st) < 0)
-      strerr_diefu2sys(111, "stat ", control) ;
-    if (!S_ISFIFO(st.st_mode))
-      strerr_diefu2x(100, control, " is not a FIFO") ;
-  }
-  fdlock = openc_create(lock) ;
-  if (fdlock < 0)
-    strerr_diefu2sys(111, "open_create ", lock) ;
-  if (lock_ex(fdlock) < 0)
-    strerr_diefu2sys(111, "lock ", lock) ;
-  fdctlw = openc_write(control) ;
-  if (fdctlw >= 0) strerr_dief1x(100, "directory already locked") ;
-  if (errno != ENXIO)
-    strerr_diefu2sys(111, "open_write ", control) ;
-  fdctl = openc_read(control) ;
-  if (fdctl < 0)
-    strerr_diefu2sys(111, "open_read ", control) ;
-  fdctlw = openc_write(control) ;
-  if (fdctlw < 0)
-    strerr_diefu2sys(111, "open_write ", control) ;
-  fd_close(fdlock) ;
-
-  return fdctl ;
-  /* we leak fdctlw but it's coe. */
-}
diff --git a/src/libs6/s6_svc_lock_release.c b/src/libs6/s6_svc_lock_release.c
deleted file mode 100644
index 4a6f68d..0000000
--- a/src/libs6/s6_svc_lock_release.c
+++ /dev/null
@@ -1,8 +0,0 @@
-/* ISC license. */
-
-#include <skalibs/djbunix.h>
-
-void s6_svc_lock_release (int fd)
-{
-  fd_close(fd) ;
-}
diff --git a/src/libs6/s6_svc_lock_take.c b/src/libs6/s6_svc_lock_take.c
deleted file mode 100644
index fcb098a..0000000
--- a/src/libs6/s6_svc_lock_take.c
+++ /dev/null
@@ -1,28 +0,0 @@
-/* ISC license. */
-
-#include <sys/stat.h>
-#include <string.h>
-#include <errno.h>
-#include <skalibs/djbunix.h>
-#include <s6/s6-supervise.h>
-
- /* XXX: does not work with dangling S6_SUPERVISE_CTLDIR symlinks */
-
-int s6_svc_lock_take (char const *dir)
-{
-  size_t dirlen = strlen(dir) ;
-  int fdlock ;
-  char lock[dirlen + sizeof(S6_SUPERVISE_CTLDIR) + 6] ;
-  memcpy(lock, dir, dirlen) ;
-  memcpy(lock + dirlen, "/" S6_SUPERVISE_CTLDIR, sizeof(S6_SUPERVISE_CTLDIR) + 1) ;
-  if ((mkdir(lock, S_IRWXU) < 0) && (errno != EEXIST)) return -1 ;
-  memcpy(lock + dirlen + sizeof(S6_SUPERVISE_CTLDIR), "/lock", 6) ;
-  fdlock = openc_create(lock) ;
-  if (fdlock < 0) return -1 ;
-  if (lock_ex(fdlock) < 0)
-  {
-    fd_close(fdlock) ;
-    return -1 ;
-  }
-  return fdlock ;
-}
diff --git a/src/libs6/s6_svc_ok.c b/src/libs6/s6_svc_ok.c
index 5e6aa27..4940071 100644
--- a/src/libs6/s6_svc_ok.c
+++ b/src/libs6/s6_svc_ok.c
@@ -2,24 +2,23 @@
 
 #include <string.h>
 #include <errno.h>
+
 #include <skalibs/djbunix.h>
+
 #include <s6/s6-supervise.h>
 
 int s6_svc_ok (char const *dir)
 {
-  size_t dirlen = strlen(dir) ;
+  int r ;
+  int e = errno ;
   int fd ;
-  char fn[dirlen + 9 + sizeof(S6_SUPERVISE_CTLDIR)] ;
+  size_t dirlen = strlen(dir) ;
+  char fn[dirlen + 6 + sizeof(S6_SUPERVISE_CTLDIR)] ;
   memcpy(fn, dir, dirlen) ;
-  fn[dirlen] = '/' ;
-  memcpy(fn + dirlen + 1, S6_SUPERVISE_CTLDIR, sizeof(S6_SUPERVISE_CTLDIR) - 1) ;
-  memcpy(fn + dirlen + sizeof(S6_SUPERVISE_CTLDIR), "/control", 9) ;
-  fd = open_write(fn) ;
-  if (fd < 0)
-  {
-    if ((errno == ENXIO) || (errno == ENOENT)) return 0 ;
-    else return -1 ;
-  }
+  memcpy(fn + dirlen, "/" S6_SUPERVISE_CTLDIR "/lock", 6 + sizeof(S6_SUPERVISE_CTLDIR)) ;
+  fd = open_read(fn) ;
+  if (fd < 0) return errno == ENOENT ? (errno = e, 0) : -1 ;
+  r = fd_islocked(fd) ;
   fd_close(fd) ;
-  return 1 ;
+  return r ;
 }
diff --git a/src/libs6/s6lockd-helper.c b/src/libs6/s6lockd-helper.c
index 8979c67..469a417 100644
--- a/src/libs6/s6lockd-helper.c
+++ b/src/libs6/s6lockd-helper.c
@@ -1,24 +1,25 @@
 /* ISC license. */
 
+#include <errno.h>
+
 #include <skalibs/allreadwrite.h>
 #include <skalibs/strerr2.h>
-#include <skalibs/env.h>
 #include <skalibs/djbunix.h>
 
 #define USAGE "s6lockd-helper lockfile"
 #define dieusage() strerr_dieusage(100, USAGE)
 
-int main (int argc, char const *const *argv, char const *const *envp)
+int main (int argc, char const *const *argv)
 {
-  int fd ;
-  char const *x = env_get2(envp, "S6LOCK_EX") ;
+  int fd, r ;
   char c ;
   PROG = "s6lockd-helper" ;
-  if (argc < 2) dieusage() ;
-  fd = open_create(argv[1]) ;
+  if (argc < 3) dieusage() ;
+  fd = open_create(argv[2]) ;
   if (fd < 0) strerr_diefu2sys(111, "open ", argv[1]) ;
-  if (((x && *x) ? lock_ex(fd) : lock_sh(fd)) < 0)
-    strerr_diefu2sys(111, "lock ", argv[1]) ;
+  r = fd_lock(fd, argv[1][0] == 'w', 0) ;
+  if (!r) errno = EBUSY ;
+  if (r < 1) strerr_diefu2sys(111, "lock ", argv[2]) ;
   if (fd_write(1, "!", 1) <= 0)
     strerr_diefu1sys(111, "write to stdout") ;
   if (fd_read(0, &c, 1) < 0)
diff --git a/src/libs6/s6lockd.c b/src/libs6/s6lockd.c
index afa8b3e..f2d18f9 100644
--- a/src/libs6/s6lockd.c
+++ b/src/libs6/s6lockd.c
@@ -131,8 +131,8 @@ static int parse_protocol (struct iovec const *v, void *context)
     case '<' : /* lock path */
     {
       s6lockio_t f = S6LOCKIO_ZERO ;
-      char const *cargv[3] = { S6LOCKD_HELPER_PROG, 0, 0 } ;
-      char const *cenvp[2] = { 0, 0 } ;
+      char const *cargv[4] = { S6LOCKD_HELPER_PROG, "r", 0, 0 } ;
+      char const *nullenv = 0 ;
       uint32_t options, pathlen ;
       if (v->iov_len < 23)
       {
@@ -150,9 +150,9 @@ static int parse_protocol (struct iovec const *v, void *context)
       f.id = id ;
       s[21] = '.' ;
       s[22] = '/' ;
-      cargv[1] = (char const *)s + 21 ;
-      if (options & S6LOCK_OPTIONS_EX) cenvp[0] = "S6LOCK_EX=1" ;
-      f.pid = child_spawn2(cargv[0], cargv, cenvp, f.p) ;
+      if (options & S6LOCK_OPTIONS_EX) cargv[1] = "w" ;
+      cargv[2] = (char const *)s + 21 ;
+      f.pid = child_spawn2(cargv[0], cargv, &nullenv, f.p) ;
       if (!f.pid)
       {
         answer(errno) ;
diff --git a/src/supervision/deps-exe/s6-svscan b/src/supervision/deps-exe/s6-svscan
index 0b76878..756dcc2 100644
--- a/src/supervision/deps-exe/s6-svscan
+++ b/src/supervision/deps-exe/s6-svscan
@@ -1,4 +1,3 @@
-${LIBS6}
 -lskarnet
 ${SYSCLOCK_LIB}
 ${SPAWN_LIB}
diff --git a/src/supervision/s6-supervise.c b/src/supervision/s6-supervise.c
index da6a187..112ccea 100644
--- a/src/supervision/s6-supervise.c
+++ b/src/supervision/s6-supervise.c
@@ -3,13 +3,16 @@
 /* For SIGWINCH */
 #include <skalibs/nonposix.h>
 
-#include <sys/wait.h>
 #include <unistd.h>
 #include <string.h>
 #include <strings.h>
 #include <errno.h>
 #include <fcntl.h>
+#include <limits.h>
 #include <signal.h>
+#include <sys/stat.h>
+#include <sys/wait.h>
+
 #include <skalibs/allreadwrite.h>
 #include <skalibs/bytestr.h>
 #include <skalibs/types.h>
@@ -20,10 +23,19 @@
 #include <skalibs/sig.h>
 #include <skalibs/selfpipe.h>
 #include <skalibs/skamisc.h>
+
 #include <s6/ftrigw.h>
 #include <s6/s6-supervise.h>
 
 #define USAGE "s6-supervise dir"
+#define CTL S6_SUPERVISE_CTLDIR "/control"
+#define LCK S6_SUPERVISE_CTLDIR "/lock"
+
+#ifdef PATH_MAX
+# define S6_PATH_MAX PATH_MAX
+#else
+# define S6_PATH_MAX 4096
+#endif
 
 typedef enum trans_e trans_t, *trans_t_ref ;
 enum trans_e
@@ -625,6 +637,83 @@ static inline void handle_control (int fd)
   }
 }
 
+static int trymkdir (char const *s)
+{
+  char buf[S6_PATH_MAX] ;
+  ssize_t r ;
+  if (mkdir(s, 0700) >= 0) return 1 ;
+  if (errno != EEXIST) strerr_diefu2sys(111, "mkdir ", s) ;
+  r = readlink(s, buf, S6_PATH_MAX) ;
+  if (r < 0)
+  {
+    struct stat st ;
+    if (errno != EINVAL)
+    {
+      errno = EEXIST ;
+      strerr_diefu2sys(111, "mkdir ", s) ;
+    }
+    if (stat(s, &st) < 0)
+      strerr_diefu2sys(111, "stat ", s) ;
+    if (!S_ISDIR(st.st_mode))
+      strerr_dief2x(100, s, " exists and is not a directory") ;
+    return 0 ;
+  }
+  else if (r == S6_PATH_MAX)
+  {
+    errno = ENAMETOOLONG ;
+    strerr_diefu2sys(111, "readlink ", s) ;
+  }
+  else
+  {
+    buf[r] = 0 ;
+    if (mkdir(buf, 0700) < 0)
+      strerr_diefu2sys(111, "mkdir ", buf) ;
+    return 1 ;
+  }
+}
+
+static inline int control_init (void)
+{
+  mode_t m = umask(0) ;
+  int fdctl, fdlck, r ;
+  if (trymkdir(S6_SUPERVISE_EVENTDIR))
+  {
+    if (chown(S6_SUPERVISE_EVENTDIR, -1, getegid()) < 0)
+      strerr_diefu1sys(111, "chown " S6_SUPERVISE_EVENTDIR) ;
+    if (chmod(S6_SUPERVISE_EVENTDIR, 03730) < 0)
+      strerr_diefu1sys(111, "chmod " S6_SUPERVISE_EVENTDIR) ;
+  }
+
+  trymkdir(S6_SUPERVISE_CTLDIR) ;
+  fdlck = open(LCK, O_WRONLY | O_NONBLOCK | O_CREAT | O_CLOEXEC, 0600) ;
+  if (fdlck < 0) strerr_diefu1sys(111, "open " LCK) ;
+  r = fd_lock(fdlck, 1, 1) ;
+  if (r < 0) strerr_diefu1sys(111, "lock " LCK) ;
+  if (!r) strerr_dief1x(100, "another instance of s6-supervise is already running") ;
+ /* fdlck leaks but it's coe */
+
+  if (mkfifo(CTL, 0600) < 0)
+  {
+    struct stat st ;
+    if (errno != EEXIST)
+      strerr_diefu1sys(111, "mkfifo " CTL) ;
+    if (stat(CTL, &st) < 0)
+      strerr_diefu1sys(111, "stat " CTL) ;
+    if (!S_ISFIFO(st.st_mode))
+      strerr_dief1x(100, CTL " is not a FIFO") ;
+  }
+  fdctl = openc_read(CTL) ;
+  if (fdctl < 0)
+    strerr_diefu1sys(111, "open " CTL " for reading") ;
+  r = openc_write(CTL) ;
+  if (r < 0)
+    strerr_diefu1sys(111, "open " CTL " for writing") ;
+ /* r leaks but it's coe */
+
+  umask(m) ;
+  return fdctl ;
+}
+
 int main (int argc, char const *const *argv)
 {
   iopause_fd x[3] = { { -1, IOPAUSE_READ, 0 }, { -1, IOPAUSE_READ, 0 }, { -1, IOPAUSE_READ, 0 } } ;
@@ -640,9 +729,7 @@ int main (int argc, char const *const *argv)
     memcpy(progname + proglen + 1, argv[1], namelen + 1) ;
     PROG = progname ;
     if (!fd_sanitize()) strerr_diefu1sys(111, "sanitize stdin and stdout") ;
-    if (!ftrigw_fifodir_make(S6_SUPERVISE_EVENTDIR, getegid(), 0))
-      strerr_diefu2sys(111, "mkfifodir ", S6_SUPERVISE_EVENTDIR) ;
-    x[1].fd = s6_supervise_lock(S6_SUPERVISE_CTLDIR) ;
+    x[1].fd = control_init() ;
     x[0].fd = selfpipe_init() ;
     if (x[0].fd == -1) strerr_diefu1sys(111, "init selfpipe") ;
     if (sig_ignore(SIGPIPE) < 0) strerr_diefu1sys(111, "ignore SIGPIPE") ;
diff --git a/src/supervision/s6-svscan.c b/src/supervision/s6-svscan.c
index 3f63c2d..1d17a3a 100644
--- a/src/supervision/s6-svscan.c
+++ b/src/supervision/s6-svscan.c
@@ -27,6 +27,8 @@
 #define USAGE "s6-svscan [ -c maxservices ] [ -t timeout ] [ -d notif ] [ -X consoleholder ] [ dir ]"
 #define dieusage() strerr_dieusage(100, USAGE)
 
+#define CTL S6_SVSCAN_CTLDIR "/control"
+#define LCK S6_SVSCAN_CTLDIR "/lock"
 #define FINISH_PROG S6_SVSCAN_CTLDIR "/finish"
 #define CRASH_PROG S6_SVSCAN_CTLDIR "/crash"
 #define SIGNAL_PROG S6_SVSCAN_CTLDIR "/SIG"
@@ -480,6 +482,49 @@ static inline void scan (void)
   }
 }
 
+static inline int control_init (void)
+{
+  mode_t m = umask(0) ;
+  int fdctl, fdlck, r ;
+  if (mkdir(S6_SVSCAN_CTLDIR, 0700) < 0)
+  {
+    struct stat st ;
+    if (errno != EEXIST)
+      strerr_diefu1sys(111, "mkdir " S6_SVSCAN_CTLDIR) ;
+    if (stat(CTL, &st) < 0)
+      strerr_diefu1sys(111, "stat " S6_SVSCAN_CTLDIR) ;
+    if (!S_ISDIR(st.st_mode))
+      strerr_dief1x(100, S6_SVSCAN_CTLDIR " exists and is not a directory") ;
+  }
+
+  fdlck = open(LCK, O_WRONLY | O_NONBLOCK | O_CREAT | O_CLOEXEC, 0600) ;
+  if (fdlck < 0) strerr_diefu1sys(111, "open " LCK) ;
+  r = fd_lock(fdlck, 1, 1) ;
+  if (r < 0) strerr_diefu1sys(111, "lock " LCK) ;
+  if (!r) strerr_dief1x(100, "another instance of s6-svscan is already running on the same directory") ;
+ /* fdlck leaks but it's coe */
+
+  if (mkfifo(CTL, 0600) < 0)
+  {
+    struct stat st ;
+    if (errno != EEXIST)
+      strerr_diefu1sys(111, "mkfifo " CTL) ;
+    if (stat(CTL, &st) < 0)
+      strerr_diefu1sys(111, "stat " CTL) ;
+    if (!S_ISFIFO(st.st_mode))
+      strerr_dief1x(100, CTL " is not a FIFO") ;
+  }
+  fdctl = openc_read(CTL) ;
+  if (fdctl < 0)
+    strerr_diefu1sys(111, "open " CTL " for reading") ;
+  r = openc_write(CTL) ;
+  if (r < 0)
+    strerr_diefu1sys(111, "open " CTL " for writing") ;
+ /* r leaks but it's coe */
+
+  umask(m) ;
+  return fdctl ;
+}
 
 int main (int argc, char const *const *argv)
 {
@@ -515,7 +560,7 @@ int main (int argc, char const *const *argv)
 
   if (argc && (chdir(argv[0]) < 0)) strerr_diefu1sys(111, "chdir") ;
   if (consoleholder && coe(consoleholder) < 0) strerr_diefu1sys(111, "coe console holder") ;
-  x[1].fd = s6_supervise_lock(S6_SVSCAN_CTLDIR) ;
+  x[1].fd = control_init() ;
   x[0].fd = selfpipe_init() ;
   if (x[0].fd < 0) strerr_diefu1sys(111, "selfpipe_init") ;