From a5bd71440e01ecd3fb6cc8bf3fcdae1fcfe11f21 Mon Sep 17 00:00:00 2001 From: Vsevolod Stakhov Date: Mon, 4 Apr 2016 13:52:06 +0100 Subject: [PATCH] [Feature] Allow to send descriptors from workers to main --- src/fuzzy_storage.c | 3 ++- src/hs_helper.c | 2 +- src/libserver/rspamd_control.c | 37 +++++++++++++++++++++++++++++++--- src/libserver/rspamd_control.h | 4 +++- 4 files changed, 40 insertions(+), 6 deletions(-) diff --git a/src/fuzzy_storage.c b/src/fuzzy_storage.c index 7a603ff58..9ca032e22 100644 --- a/src/fuzzy_storage.c +++ b/src/fuzzy_storage.c @@ -1471,7 +1471,8 @@ start_fuzzy (struct rspamd_worker *worker) memset (srv_cmd.cmd.spair.pair_id, 0, sizeof (srv_cmd.cmd.spair.pair_id)); memcpy (srv_cmd.cmd.spair.pair_id, "fuzzy", sizeof ("fuzzy")); - rspamd_srv_send_command (worker, ctx->ev_base, &srv_cmd, fuzzy_peer_rep, ctx); + rspamd_srv_send_command (worker, ctx->ev_base, &srv_cmd, -1, + fuzzy_peer_rep, ctx); event_base_loop (ctx->ev_base, 0); rspamd_worker_block_signals (); diff --git a/src/hs_helper.c b/src/hs_helper.c index e0c56f4d2..5f955561d 100644 --- a/src/hs_helper.c +++ b/src/hs_helper.c @@ -195,7 +195,7 @@ rspamd_rs_compile (struct hs_helper_ctx *ctx, struct rspamd_worker *worker, srv_cmd.cmd.hs_loaded.cache_dir = ctx->hs_dir; srv_cmd.cmd.hs_loaded.forced = forced; - rspamd_srv_send_command (worker, ctx->ev_base, &srv_cmd, NULL, NULL); + rspamd_srv_send_command (worker, ctx->ev_base, &srv_cmd, -1, NULL, NULL); return TRUE; } diff --git a/src/libserver/rspamd_control.c b/src/libserver/rspamd_control.c index 84f68de02..626198bd2 100644 --- a/src/libserver/rspamd_control.c +++ b/src/libserver/rspamd_control.c @@ -690,8 +690,15 @@ rspamd_srv_handler (gint fd, short what, gpointer ud) if (what == EV_READ) { worker = ud; srv = worker->srv; + iov.iov_base = &cmd; + iov.iov_len = sizeof (cmd); + memset (&msg, 0, sizeof (msg)); + msg.msg_control = fdspace; + msg.msg_controllen = sizeof (fdspace); + msg.msg_iov = &iov; + msg.msg_iovlen = 1; - r = read (fd, &cmd, sizeof (cmd)); + r = recvmsg (fd, &msg, 0); if (r == -1) { msg_err ("cannot read from worker's srv pipe: %s", @@ -824,6 +831,7 @@ rspamd_srv_start_watching (struct rspamd_worker *worker, struct rspamd_srv_request_data { struct rspamd_worker *worker; struct rspamd_srv_command cmd; + gint attached_fd; struct rspamd_srv_reply rep; rspamd_srv_reply_handler handler; struct event io_ev; @@ -837,12 +845,32 @@ rspamd_srv_request_handler (gint fd, short what, gpointer ud) struct msghdr msg; struct iovec iov; guchar fdspace[CMSG_SPACE(sizeof (int))]; + struct cmsghdr *cmsg; gssize r; gint rfd = -1; if (what == EV_WRITE) { /* Send request to server */ - r = write (fd, &rd->cmd, sizeof (rd->cmd)); + memset (&msg, 0, sizeof (msg)); + + /* Attach fd to the message */ + if (rd->attached_fd != -1) { + memset (fdspace, 0, sizeof (fdspace)); + msg.msg_control = fdspace; + msg.msg_controllen = sizeof (fdspace); + cmsg = CMSG_FIRSTHDR (&msg); + cmsg->cmsg_level = SOL_SOCKET; + cmsg->cmsg_type = SCM_RIGHTS; + cmsg->cmsg_len = CMSG_LEN (sizeof (int)); + memcpy (CMSG_DATA (cmsg), &rd->attached_fd, sizeof (int)); + } + + iov.iov_base = &rd->cmd; + iov.iov_len = sizeof (rd->cmd); + msg.msg_iov = &iov; + msg.msg_iovlen = 1; + + r = sendmsg (fd, &msg, 0); if (r == -1) { msg_err ("cannot write to server pipe: %s", strerror (errno)); @@ -898,7 +926,9 @@ void rspamd_srv_send_command (struct rspamd_worker *worker, struct event_base *ev_base, struct rspamd_srv_command *cmd, - rspamd_srv_reply_handler handler, gpointer ud) + gint attached_fd, + rspamd_srv_reply_handler handler, + gpointer ud) { struct rspamd_srv_request_data *rd; @@ -912,6 +942,7 @@ rspamd_srv_send_command (struct rspamd_worker *worker, rd->worker = worker; rd->rep.id = cmd->id; rd->rep.type = cmd->type; + rd->attached_fd = attached_fd; event_set (&rd->io_ev, worker->srv_pipe[1], EV_WRITE, rspamd_srv_request_handler, rd); diff --git a/src/libserver/rspamd_control.h b/src/libserver/rspamd_control.h index 751b916eb..dbe1001d6 100644 --- a/src/libserver/rspamd_control.h +++ b/src/libserver/rspamd_control.h @@ -177,5 +177,7 @@ void rspamd_srv_start_watching (struct rspamd_worker *worker, void rspamd_srv_send_command (struct rspamd_worker *worker, struct event_base *ev_base, struct rspamd_srv_command *cmd, - rspamd_srv_reply_handler handler, gpointer ud); + gint attached_fd, + rspamd_srv_reply_handler handler, + gpointer ud); #endif -- 2.39.5