[SCM] Samba Shared Repository - branch master updated

Martin Schwenke martins at samba.org
Fri Sep 1 10:50:02 UTC 2017


The branch, master has been updated
       via  dccd963 ctdb-client: Use sock_client abstraction for eventd client
       via  dcc1eaf ctdb-common: Add sock_client abstraction
       via  dfa8786 ctdb-protocol: Drop struct ctdb_event_header
       via  164d65a ctdb-protocol: Replace ctdb_event_header with sock_packet_header
       via  1787a4b ctdb-protocol: Add a generic packet header
      from  15c9177 ctdb-common: Parse IPv4-mapped IPv6 addresses into IPv4 addresses

https://git.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit dccd9630fb6d82cbf79374c75cd305987c9c9eb8
Author: Amitay Isaacs <amitay at gmail.com>
Date:   Thu Jun 29 16:25:57 2017 +1000

    ctdb-client: Use sock_client abstraction for eventd client
    
    Signed-off-by: Amitay Isaacs <amitay at gmail.com>
    Reviewed-by: Martin Schwenke <martin at meltin.net>
    
    Autobuild-User(master): Martin Schwenke <martins at samba.org>
    Autobuild-Date(master): Fri Sep  1 12:49:27 CEST 2017 on sn-devel-144

commit dcc1eaf542e279bf05c338fd03bc9307084cadc5
Author: Amitay Isaacs <amitay at gmail.com>
Date:   Thu Jun 29 15:10:11 2017 +1000

    ctdb-common: Add sock_client abstraction
    
    This sets up boilerplate required for a client code connecting to a
    server over unix domain socket.  The communication between client
    and server is "request" from client to server and "reply" from
    server to client.
    
    Signed-off-by: Amitay Isaacs <amitay at gmail.com>
    Reviewed-by: Martin Schwenke <martin at meltin.net>

commit dfa87862fb3f2c17094bb8ac921b369c344c556d
Author: Amitay Isaacs <amitay at gmail.com>
Date:   Tue Jul 11 02:16:24 2017 +1000

    ctdb-protocol: Drop struct ctdb_event_header
    
    Signed-off-by: Amitay Isaacs <amitay at gmail.com>
    Reviewed-by: Martin Schwenke <martin at meltin.net>

commit 164d65ace283188d00224dd1e001b8776d393fd8
Author: Amitay Isaacs <amitay at gmail.com>
Date:   Mon Jul 10 18:35:12 2017 +1000

    ctdb-protocol: Replace ctdb_event_header with sock_packet_header
    
    This removes the static declaration and adds prototype declarations
    of ctdb_event_header marshalling functions to avoid compiler warnings.
    These functions will be removed.
    
    Signed-off-by: Amitay Isaacs <amitay at gmail.com>
    Reviewed-by: Martin Schwenke <martin at meltin.net>

commit 1787a4b63292aee0e9df4e4031188ac239d804d8
Author: Amitay Isaacs <amitay at gmail.com>
Date:   Fri Jul 7 17:21:54 2017 +1000

    ctdb-protocol: Add a generic packet header
    
    This will avoid duplication when new daemons (and new client-server
    protocols) are created out of the main ctdb daemon.
    
    Signed-off-by: Amitay Isaacs <amitay at gmail.com>
    Reviewed-by: Martin Schwenke <martin at meltin.net>

-----------------------------------------------------------------------

Summary of changes:
 ctdb/client/client_event.c             | 297 +++++++----------------------
 ctdb/common/sock_client.c              | 332 +++++++++++++++++++++++++++++++++
 ctdb/common/sock_client.h              | 129 +++++++++++++
 ctdb/protocol/protocol.h               |  18 +-
 ctdb/protocol/protocol_api.h           |  15 +-
 ctdb/protocol/protocol_event.c         |  61 +-----
 ctdb/protocol/protocol_sock.c          |  81 ++++++++
 ctdb/server/ctdb_eventd.c              |   3 +-
 ctdb/server/eventscript.c              |   3 +-
 ctdb/tests/cunit/protocol_test_102.sh  |   1 -
 ctdb/tests/src/protocol_common.c       |  13 ++
 ctdb/tests/src/protocol_common.h       |   4 +
 ctdb/tests/src/protocol_common_event.c |  21 +--
 ctdb/tests/src/protocol_common_event.h |   4 -
 ctdb/tests/src/protocol_event_test.c   |  32 +---
 ctdb/tests/src/protocol_types_test.c   |   5 +
 ctdb/wscript                           |   6 +-
 17 files changed, 679 insertions(+), 346 deletions(-)
 create mode 100644 ctdb/common/sock_client.c
 create mode 100644 ctdb/common/sock_client.h
 create mode 100644 ctdb/protocol/protocol_sock.c


Changeset truncated at 500 lines:

diff --git a/ctdb/client/client_event.c b/ctdb/client/client_event.c
index 533ed39..7111fe7 100644
--- a/ctdb/client/client_event.c
+++ b/ctdb/client/client_event.c
@@ -18,7 +18,6 @@
 */
 
 #include "replace.h"
-#include "system/filesys.h"
 #include "system/network.h"
 
 #include <talloc.h>
@@ -28,301 +27,149 @@
 #include "lib/util/tevent_unix.h"
 
 #include "common/logging.h"
-#include "common/reqid.h"
-#include "common/comm.h"
+#include "common/sock_client.h"
 
 #include "protocol/protocol_api.h"
 
 #include "client/client_event.h"
 
 struct ctdb_event_context {
-	struct reqid_context *idr;
-	struct comm_context *comm;
-	int fd;
-
-	ctdb_client_callback_func_t callback;
-	void *private_data;
+	struct sock_client_context *sockc;
 };
 
-static int ctdb_event_connect(struct ctdb_event_context *eclient,
-			      struct tevent_context *ev,
-			      const char *sockpath);
-
-static int ctdb_event_context_destructor(struct ctdb_event_context *eclient);
-
-int ctdb_event_init(TALLOC_CTX *mem_ctx, struct tevent_context *ev,
-		    const char *sockpath, struct ctdb_event_context **out)
+static int ctdb_event_msg_request_push(void *request_data, uint32_t reqid,
+				       TALLOC_CTX *mem_ctx,
+				       uint8_t **buf, size_t *buflen,
+				       void *private_data)
 {
-	struct ctdb_event_context *eclient;
+	struct ctdb_event_request *request =
+		(struct ctdb_event_request *)request_data;
 	int ret;
 
-	eclient = talloc_zero(mem_ctx, struct ctdb_event_context);
-	if (eclient == NULL) {
-		DEBUG(DEBUG_ERR, (__location__ " memory allocation error\n"));
-		return ENOMEM;
-	}
+	sock_packet_header_set_reqid(&request->header, reqid);
 
-	ret = reqid_init(eclient, INT_MAX-200, &eclient->idr);
-	if (ret != 0) {
-		DEBUG(DEBUG_ERR, ("reqid_init() failed, ret=%d\n", ret));
-		talloc_free(eclient);
-		return ret;
+	*buflen = ctdb_event_request_len(request);
+	*buf = talloc_size(mem_ctx, *buflen);
+	if (*buf == NULL) {
+		return ENOMEM;
 	}
 
-	eclient->fd = -1;
-
-	ret = ctdb_event_connect(eclient, ev, sockpath);
+	ret = ctdb_event_request_push(request, *buf, buflen);
 	if (ret != 0) {
-		talloc_free(eclient);
 		return ret;
 	}
 
-	talloc_set_destructor(eclient, ctdb_event_context_destructor);
-
-	*out = eclient;
 	return 0;
 }
 
-static int ctdb_event_context_destructor(struct ctdb_event_context *eclient)
+static int ctdb_event_msg_reply_pull(uint8_t *buf, size_t buflen,
+				     TALLOC_CTX *mem_ctx, void **reply_data,
+				     void *private_data)
 {
-	if (eclient->fd != -1) {
-		close(eclient->fd);
-		eclient->fd = -1;
-	}
-	return 0;
-}
-
-static void event_read_handler(uint8_t *buf, size_t buflen,
-			       void *private_data);
-static void event_dead_handler(void *private_data);
-
-static int ctdb_event_connect(struct ctdb_event_context *eclient,
-			      struct tevent_context *ev, const char *sockpath)
-{
-	struct sockaddr_un addr;
-	size_t len;
-	int fd, ret;
-
-	if (sockpath == NULL) {
-		DEBUG(DEBUG_ERR, ("socket path cannot be NULL\n"));
-		return EINVAL;
-	}
+	struct ctdb_event_reply *reply;
+	int ret;
 
-	memset(&addr, 0, sizeof(addr));
-	addr.sun_family = AF_UNIX;
-	len = strlcpy(addr.sun_path, sockpath, sizeof(addr.sun_path));
-	if (len >= sizeof(addr.sun_path)) {
-		DEBUG(DEBUG_ERR, ("socket path too long, len=%zu\n",
-				  strlen(sockpath)));
-		return ENAMETOOLONG;
+	reply = talloc_zero(mem_ctx, struct ctdb_event_reply);
+	if (reply == NULL) {
+		return ENOMEM;
 	}
 
-	fd = socket(AF_UNIX, SOCK_STREAM, 0);
-	if (fd == -1) {
-		ret = errno;
-		DEBUG(DEBUG_ERR, ("socket() failed, errno=%d\n", ret));
+	ret = ctdb_event_reply_pull(buf, buflen, reply, reply);
+	if (ret != 0) {
+		talloc_free(reply);
 		return ret;
 	}
 
-	ret = connect(fd, (struct sockaddr *)&addr, sizeof(addr));
-	if (ret == -1) {
-		ret = errno;
-		DEBUG(DEBUG_ERR, ("connect() failed, errno=%d\n", ret));
-		close(fd);
-		return ret;
-	}
-	eclient->fd = fd;
+	*reply_data = reply;
+	return 0;
+}
 
-	ret = comm_setup(eclient, ev, fd, event_read_handler, eclient,
-			 event_dead_handler, eclient, &eclient->comm);
+static int ctdb_event_msg_reply_reqid(uint8_t *buf, size_t buflen,
+				      uint32_t *reqid, void *private_data)
+{
+	struct sock_packet_header header;
+	size_t np;
+	int ret;
+
+	ret = sock_packet_header_pull(buf, buflen, &header, &np);
 	if (ret != 0) {
-		DEBUG(DEBUG_ERR, ("comm_setup() failed, ret=%d\n", ret));
-		close(fd);
-		eclient->fd = -1;
 		return ret;
 	}
 
+	*reqid = header.reqid;
 	return 0;
 }
 
-static void ctdb_event_msg_reply(struct ctdb_event_context *eclient,
-				 uint8_t *buf, size_t buflen);
+struct sock_client_proto_funcs event_proto_funcs = {
+	.request_push = ctdb_event_msg_request_push,
+	.reply_pull = ctdb_event_msg_reply_pull,
+	.reply_reqid = ctdb_event_msg_reply_reqid,
+};
 
-static void event_read_handler(uint8_t *buf, size_t buflen,
-			       void *private_data)
+
+int ctdb_event_init(TALLOC_CTX *mem_ctx, struct tevent_context *ev,
+		    const char *sockpath, struct ctdb_event_context **out)
 {
-	struct ctdb_event_context *eclient = talloc_get_type_abort(
-		private_data, struct ctdb_event_context);
+	struct ctdb_event_context *eclient;
+	int ret;
 
-	ctdb_event_msg_reply(eclient, buf, buflen);
-}
+	eclient = talloc_zero(mem_ctx, struct ctdb_event_context);
+	if (eclient == NULL) {
+		DEBUG(DEBUG_ERR, (__location__ " memory allocation error\n"));
+		return ENOMEM;
+	}
 
-static void event_dead_handler(void *private_data)
-{
-	struct ctdb_event_context *eclient = talloc_get_type_abort(
-		private_data, struct ctdb_event_context);
-	ctdb_client_callback_func_t callback = eclient->callback;
-	void *callback_data = eclient->private_data;
-
-	talloc_free(eclient);
-	if (callback != NULL) {
-		callback(callback_data);
-		return;
+	ret = sock_client_setup(eclient, ev, sockpath,
+				&event_proto_funcs, eclient,
+				&eclient->sockc);
+	if (ret != 0) {
+		talloc_free(eclient);
+		return ret;
 	}
 
-	DEBUG(DEBUG_NOTICE, ("connection to daemon closed, exiting\n"));
-	exit(1);
+	*out = eclient;
+	return 0;
 }
 
 void ctdb_event_set_disconnect_callback(struct ctdb_event_context *eclient,
 					ctdb_client_callback_func_t callback,
 					void *private_data)
 {
-	eclient->callback = callback;
-	eclient->private_data = private_data;
+	sock_client_set_disconnect_callback(eclient->sockc,
+					    callback, private_data);
 }
 
 /*
  * Handle eventd_request and eventd_reply
  */
 
-struct ctdb_event_msg_state {
-	struct ctdb_event_context *eclient;
-
-	uint32_t reqid;
-	struct tevent_req *req;
-	struct ctdb_event_reply *reply;
-};
-
-static int ctdb_event_msg_state_destructor(struct ctdb_event_msg_state *state);
-static void ctdb_event_msg_done(struct tevent_req *subreq);
-
 struct tevent_req *ctdb_event_msg_send(TALLOC_CTX *mem_ctx,
 				       struct tevent_context *ev,
 				       struct ctdb_event_context *eclient,
 				       struct ctdb_event_request *request)
 {
-	struct tevent_req *req, *subreq;
-	struct ctdb_event_msg_state *state;
-	uint8_t *buf;
-	size_t buflen;
-	int ret;
-
-	req = tevent_req_create(mem_ctx, &state, struct ctdb_event_msg_state);
-	if (req == NULL) {
-		return NULL;
-	}
-
-	state->eclient = eclient;
-
-	state->reqid = reqid_new(eclient->idr, state);
-	if (state->reqid == REQID_INVALID) {
-		talloc_free(req);
-		return NULL;
-	}
-	state->req = req;
-
-	talloc_set_destructor(state, ctdb_event_msg_state_destructor);
-
-	ctdb_event_header_fill(&request->header, state->reqid);
-
-	buflen = ctdb_event_request_len(request);
-	buf = talloc_size(state, buflen);
-	if (tevent_req_nomem(buf, req)) {
-		return tevent_req_post(req, ev);
-	}
-
-	ret = ctdb_event_request_push(request, buf, &buflen);
-	if (ret != 0) {
-		tevent_req_error(req, ret);
-		return tevent_req_post(req, ev);
-	}
-
-	subreq = comm_write_send(state, ev, eclient->comm, buf, buflen);
-	if (tevent_req_nomem(subreq, req)) {
-		return tevent_req_post(req, ev);
-	}
-	tevent_req_set_callback(subreq, ctdb_event_msg_done, req);
+	struct tevent_req *req;
 
+	req = sock_client_msg_send(mem_ctx, ev, eclient->sockc,
+				   tevent_timeval_zero(), request);
 	return req;
 }
 
-static int ctdb_event_msg_state_destructor(struct ctdb_event_msg_state *state)
-{
-	reqid_remove(state->eclient->idr, state->reqid);
-	return 0;
-}
-
-static void ctdb_event_msg_done(struct tevent_req *subreq)
-{
-	struct tevent_req *req = tevent_req_callback_data(
-		subreq, struct tevent_req);
-	int ret;
-	bool status;
-
-	status = comm_write_recv(subreq, &ret);
-	TALLOC_FREE(subreq);
-	if (! status) {
-		tevent_req_error(req, ret);
-		return;
-	}
-
-	/* Wait for the reply or timeout */
-}
-
-static void ctdb_event_msg_reply(struct ctdb_event_context *eclient,
-				 uint8_t *buf, size_t buflen)
-{
-	struct ctdb_event_reply *reply;
-	struct ctdb_event_msg_state *state;
-	int ret;
-
-	reply = talloc_zero(eclient, struct ctdb_event_reply);
-	if (reply == NULL) {
-		D_WARNING("memory allocation error\n");
-		return;
-	}
-
-	ret = ctdb_event_reply_pull(buf, buflen, reply, reply);
-	if (ret != 0) {
-		D_WARNING("Invalid packet received, ret=%d\n", ret);
-		return;
-	}
-
-	state = reqid_find(eclient->idr, reply->header.reqid,
-			   struct ctdb_event_msg_state);
-	if (state == NULL) {
-		return;
-	}
-
-	if (reply->header.reqid != state->reqid) {
-		return;
-	}
-
-	state->reply = talloc_steal(state, reply);
-	tevent_req_done(state->req);
-}
-
 bool ctdb_event_msg_recv(struct tevent_req *req, int *perr,
 			 TALLOC_CTX *mem_ctx,
 			 struct ctdb_event_reply **reply)
 {
-	struct ctdb_event_msg_state *state = tevent_req_data(
-		req, struct ctdb_event_msg_state);
-	int ret;
+	void *reply_data;
+	bool status;
 
-	if (tevent_req_is_unix_error(req, &ret)) {
-		if (perr != NULL) {
-			*perr = ret;
-		}
-		return false;
-	}
+	status = sock_client_msg_recv(req, perr, mem_ctx, &reply_data);
 
-	if (reply != NULL) {
-		*reply = talloc_steal(mem_ctx, state->reply);
+	if (status && reply != NULL) {
+		*reply = talloc_get_type_abort(
+				reply_data, struct ctdb_event_reply);
 	}
 
-	return true;
+	return status;
 }
 
 /*
diff --git a/ctdb/common/sock_client.c b/ctdb/common/sock_client.c
new file mode 100644
index 0000000..e5f993e
--- /dev/null
+++ b/ctdb/common/sock_client.c
@@ -0,0 +1,332 @@
+/*
+   A client based on unix domain socket
+
+   Copyright (C) Amitay Isaacs  2017
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 3 of the License, or
+   (at your option) any later version.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "replace.h"
+#include "system/filesys.h"
+#include "system/network.h"
+
+#include <talloc.h>
+#include <tevent.h>
+
+#include "lib/util/debug.h"
+#include "lib/util/time.h"
+#include "lib/util/tevent_unix.h"
+
+#include "common/logging.h"
+#include "common/reqid.h"
+#include "common/comm.h"
+#include "common/sock_client.h"
+
+struct sock_client_context {
+	struct sock_client_proto_funcs *funcs;
+	void *private_data;
+
+	void (*disconnect_callback)(void *private_data);
+	void *disconnect_data;
+
+	int fd;
+	struct comm_context *comm;
+	struct reqid_context *idr;
+};
+
+/*
+ * connect to a unix domain socket
+ */
+
+static int socket_connect(const char *sockpath)
+{
+	struct sockaddr_un addr;
+	size_t len;
+	int fd, ret;
+
+	memset(&addr, 0, sizeof(addr));
+	addr.sun_family = AF_UNIX;
+
+	len = strlcpy(addr.sun_path, sockpath, sizeof(addr.sun_path));
+	if (len >= sizeof(addr.sun_path)) {
+		D_ERR("socket path too long: %s\n", sockpath);
+		return -1;
+	}
+
+	fd = socket(AF_UNIX, SOCK_STREAM, 0);
+	if (fd == -1) {
+		D_ERR("socket create failed - %s\n", sockpath);
+		return -1;
+	}
+
+	ret = connect(fd, (struct sockaddr *)&addr, sizeof(addr));
+	if (ret != 0) {
+		D_ERR("socket connect failed - %s\n", sockpath);
+		close(fd);
+		return -1;
+	}
+
+	return fd;
+}
+
+/*
+ * Socket client
+ */
+
+static int sock_client_context_destructor(struct sock_client_context *sockc);
+static void sock_client_read_handler(uint8_t *buf, size_t buflen,
+				     void *private_data);
+static void sock_client_dead_handler(void *private_data);
+
+static void sock_client_msg_reply(struct sock_client_context *sockc,
+				  uint8_t *buf, size_t buflen);
+
+int sock_client_setup(TALLOC_CTX *mem_ctx, struct tevent_context *ev,
+		      const char *sockpath,
+		      struct sock_client_proto_funcs *funcs,
+		      void *private_data,
+		      struct sock_client_context **result)
+{
+	struct sock_client_context *sockc;
+	int ret;
+
+	if (sockpath == NULL) {
+		return EINVAL;
+	}
+
+	if (funcs == NULL || funcs->request_push == NULL ||


-- 
Samba Shared Repository



More information about the samba-cvs mailing list