#include "hostpid.h"
#include "array.h"
#include "ioloop.h"
+#include "sleep.h"
#include "test-common.h"
#include "test-subprocess.h"
volatile sig_atomic_t test_subprocess_is_child = 0;
static bool test_subprocess_lib_init = FALSE;
+static volatile bool test_subprocess_notification_signal_received = FALSE;
static struct event *test_subprocess_event = NULL;
static ARRAY(struct test_subprocess *) test_subprocesses = ARRAY_INIT;
static void (*test_subprocess_cleanup_callback)(void) = NULL;
test_subprocess_cleanup_callback = callback;
}
+void test_subprocess_notify_signal_send(pid_t pid)
+{
+ if (kill(pid, SIGHUP) < 0)
+ i_fatal("kill(%ld, SIGHUP) failed: %m", (long)pid);
+}
+
+void test_subprocess_notify_signal_send_parent(void)
+{
+ test_subprocess_notify_signal_send(getppid());
+}
+
+void test_subprocess_notify_signal_reset(void)
+{
+ test_subprocess_notification_signal_received = FALSE;
+}
+
+void test_subprocess_notify_signal_wait(unsigned int timeout_msecs)
+{
+ unsigned int i, count = timeout_msecs / 10;
+
+ for (i = 0; i < count; i++) {
+ if (test_subprocess_notification_signal_received)
+ return;
+ i_sleep_msecs(10);
+ }
+ i_fatal("Didn't receive wait notification signal from server");
+}
+
+static void
+test_subprocess_notification_signal(const siginfo_t *si ATTR_UNUSED,
+ void *context ATTR_UNUSED)
+{
+ test_subprocess_notification_signal_received = TRUE;
+}
+
void test_subprocesses_init(bool debug)
{
if (!lib_is_initialized()) {
lib_signals_set_handler(SIGINT, 0, test_subprocess_terminate, NULL);
lib_signals_set_handler(SIGSEGV, 0, test_subprocess_terminate, NULL);
lib_signals_set_handler(SIGABRT, 0, test_subprocess_terminate, NULL);
+ lib_signals_set_handler(SIGHUP, LIBSIG_FLAG_RESTART,
+ test_subprocess_notification_signal, NULL);
i_array_init(&test_subprocesses, 8);
exit()s unexpectedly. Note that this may be run in signal context. */
void test_subprocess_set_cleanup_callback(void (*callback)(void));
+/* Send a notification signal (SIGHUP) to the given PID */
+void test_subprocess_notify_signal_send(pid_t pid);
+/* Send a notificatino signal to the parent process. */
+void test_subprocess_notify_signal_send_parent(void);
+/* Reset any previously sent notification signals. */
+void test_subprocess_notify_signal_reset(void);
+/* Wait until a notification signal is sent, or return immediately if it was
+ already sent. test_subprocess_notify_signal_reset() should be called before
+ this to make sure it's not returning due to a previously sent signal.
+ If the timeout is reached, i_fatal() is called. */
+void test_subprocess_notify_signal_wait(unsigned int timeout_msecs);
+
void test_subprocesses_init(bool debug);
void test_subprocesses_deinit(void);