#include "mons_handlers.h"
+static void mons_sweep_procs(MONS_INSTANCE *mons);
+
static int mons_destructor(void *object)
{
MONS_INSTANCE *mons = talloc_get_type_abort(object, MONS_INSTANCE);
- if (mons->handlers) {
+ if (mons->handlers)
g_ptr_array_unref(mons->handlers);
- }
+
+ if (mons->pids)
+ g_array_unref(mons->pids);
+
return 0;
}
talloc_free(mons);
return NULL;
}
+
+ mons->pids = g_array_new(FALSE, FALSE, sizeof(pid_t));
+ if (mons->pids == NULL) {
+ talloc_free(mons);
+ return NULL;
+ }
}
return mons;
}
int conn=-1;
int pid=-1;
- if (0 > (conn = accept(listen, NULL, NULL))) {
- perror("Error from monitoring interface accept()");
+ if (0 > (conn = tr_sock_accept(listen))) {
+ tr_err("mons_accept: Error accepting connection");
return 1;
}
if (pid == 0) {
close(listen);
- tr_gss_handle_connection(conn,
- "trustmonitor", mons->hostname, /* acceptor name */
- mons->auth_handler, mons->cookie, /* auth callback and cookie */
- mons_req_cb, mons /* req callback and cookie */
- );
+ switch(tr_gss_handle_connection(conn,
+ "trustmonitor", mons->hostname, /* acceptor name */
+ mons->auth_handler, mons->cookie, /* auth callback and cookie */
+ mons_req_cb, mons /* req callback and cookie */
+ )) {
+ case TR_GSS_SUCCESS:
+ /* do nothing */
+ break;
+
+ case TR_GSS_ERROR:
+ tr_debug("mons_accept: Error returned by tr_gss_handle_connection()");
+ break;
+
+ default:
+ tr_err("mons_accept: Unexpected value returned by tr_gss_handle_connection()");
+ break;
+ }
close(conn);
exit(0); /* exit to kill forked child process */
- } else {
- close(conn);
}
+ /* Only the parent process gets here */
+ close(conn);
+ g_array_append_val(mons->pids, pid);
+
/* clean up any processes that have completed */
- while (waitpid(-1, 0, WNOHANG) > 0);
+ mons_sweep_procs(mons);
return 0;
}
+
+void mons_sweep_procs(MONS_INSTANCE *mons)
+{
+ guint ii;
+ pid_t pid;
+ int status;
+
+ /* loop backwards over the array so we can remove elements as we go */
+ for (ii=mons->pids->len; ii > 0; ii--) {
+ /* ii-1 is the current index */
+ pid = g_array_index(mons->pids, pid_t, ii-1);
+ if (waitpid(pid, &status, WNOHANG) > 0) {
+ /* the process exited */
+ tr_debug("mons_sweep_procs: monitoring process %d terminated.", pid);
+
+ g_array_remove_index_fast(mons->pids, ii-1); /* disturbs only indices >= ii-1 which we've already handled */
+ if (WIFEXITED(status)) {
+ if (WEXITSTATUS(status) == 0)
+ tr_debug("mons_sweep_procs: monitoring process %d succeeded.", pid);
+ else
+ tr_debug("mons_sweep_procs: monitoring process %d exited with status %d.", pid, WTERMSIG(status));
+ } else if (WIFSIGNALED(status)) {
+ tr_debug("mons_sweep_procs: monitoring process %d terminated by signal %d.", pid, WTERMSIG(status));
+ }
+ }
+ }
+}