The branch, master has been updated
       via  c1b4a74 ctdb-common: Add async version of shutdown in sock_daemon
       via  41d888a ctdb-common: Add async version of reconfigure in sock_daemon
       via  7558592 ctdb-common: Add async version of startup in sock_daemon
       via  ba3e9e6 ctdb-tests: Create sock_daemon_funcs per test
       via  3b8f0cc ctdb-common: Handle errors on unexpected socket close in 
sock_daemon
       via  984c3f4 ctdb-common: Start listening to sockets only on successful 
startup
       via  001ae55 ctdb-common: Start wait computation only after successful 
startup
       via  fbb5ac8 ctdb-common: Return status from sock_daemon 
startup()/reconfigure()
       via  a6296ba ctdb-common: Do not use sock->req outside sock_socket 
functions
       via  49308f7 ctdb-common: Call missing tevent_wakeup_recv() in 
sock_daemon
       via  848f242 ctdb-daemon: Allocate deferred calls off calling context
       via  757a120 s3: utils: net. Fix return paths that don't free talloc 
stackframe.
      from  6e7d037 Fix formating of sources to be less than 80 lines

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


- Log -----------------------------------------------------------------
commit c1b4a74f272977ebdc735c040e976853c7ca800f
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 17 12:38:47 2017 +1100

    ctdb-common: Add async version of shutdown in sock_daemon
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>
    
    Autobuild-User(master): Martin Schwenke <[email protected]>
    Autobuild-Date(master): Tue Nov 21 08:58:45 CET 2017 on sn-devel-144

commit 41d888afbecfca6e4ea3c6c86c05101bd5e5b5c4
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 17 12:38:18 2017 +1100

    ctdb-common: Add async version of reconfigure in sock_daemon
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 7558592d15fa4911fa8d2061aa56e2b151f516a2
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 17 12:36:29 2017 +1100

    ctdb-common: Add async version of startup in sock_daemon
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit ba3e9e6eae62af0ee991945206e0ef2b3dba8acf
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 17 13:11:12 2017 +1100

    ctdb-tests: Create sock_daemon_funcs per test
    
    This avoids defining sock_daemon functions that are not needed in the test.
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 3b8f0cc21dd18e84ee78d0450d6f89435abf8dc1
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 17 12:31:16 2017 +1100

    ctdb-common: Handle errors on unexpected socket close in sock_daemon
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 984c3f4f66846fb05fbbbc0cb4d2a3d2cacb6444
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 10 12:15:45 2017 +1100

    ctdb-common: Start listening to sockets only on successful startup
    
    Fix tests to use wait_send() instead of startup() as a synchronization
    point to ensure that the socket is listening.
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 001ae55011d9c0596f398dc374efc84637f1590c
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 17 10:52:57 2017 +1100

    ctdb-common: Start wait computation only after successful startup
    
    This orders the startup events in sock_daemon code.
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit fbb5ac8404525a0828504cd744992dfcb7c8e216
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 10 12:10:05 2017 +1100

    ctdb-common: Return status from sock_daemon startup()/reconfigure()
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit a6296bad87ac16cb0a39d35aa8cf0db2f85ec0d3
Author: Amitay Isaacs <[email protected]>
Date:   Mon Nov 20 11:52:55 2017 +1100

    ctdb-common: Do not use sock->req outside sock_socket functions
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 49308f7f22f3d6fa05cc81fdef3db020e503fa9f
Author: Amitay Isaacs <[email protected]>
Date:   Fri Nov 10 12:18:01 2017 +1100

    ctdb-common: Call missing tevent_wakeup_recv() in sock_daemon
    
    https://bugzilla.samba.org/show_bug.cgi?id=13153
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 848f2425984667c243ccac847b8f48a66ce10178
Author: Amitay Isaacs <[email protected]>
Date:   Thu Oct 19 14:58:18 2017 +1100

    ctdb-daemon: Allocate deferred calls off calling context
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13152
    
    This makes sure that if a client disconnects, all the deferred calls
    from the client are correctly freed.
    
    Signed-off-by: Amitay Isaacs <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

commit 757a120fc4c659047bd6a1175b24f0673630ce2d
Author: Jeremy Allison <[email protected]>
Date:   Tue Nov 21 00:09:39 2017 +0000

    s3: utils: net. Fix return paths that don't free talloc stackframe.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=13151
    
    Signed-off-by: Jeremy Allison <[email protected]>
    Reviewed-by: Martin Schwenke <[email protected]>

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

Summary of changes:
 ctdb/common/sock_daemon.c                | 271 ++++++++++++++++---
 ctdb/common/sock_daemon.h                |  41 ++-
 ctdb/server/ctdb_call.c                  |  14 +-
 ctdb/tests/cunit/sock_daemon_test_001.sh |  33 ++-
 ctdb/tests/src/sock_daemon_test.c        | 449 +++++++++++++++++++++++++++----
 source3/utils/net_usershare.c            |   5 +-
 6 files changed, 707 insertions(+), 106 deletions(-)


Changeset truncated at 500 lines:

diff --git a/ctdb/common/sock_daemon.c b/ctdb/common/sock_daemon.c
index ba171af..7554cd6 100644
--- a/ctdb/common/sock_daemon.c
+++ b/ctdb/common/sock_daemon.c
@@ -265,7 +265,11 @@ static int sock_socket_init(TALLOC_CTX *mem_ctx, const 
char *sockpath,
                return ENOMEM;
        }
 
-       sock->sockpath = sockpath;
+       sock->sockpath = talloc_strdup(sock, sockpath);
+       if (sock->sockpath == NULL) {
+               talloc_free(sock);
+               return ENOMEM;
+       }
        sock->funcs = funcs;
        sock->private_data = private_data;
        sock->fd = -1;
@@ -278,6 +282,8 @@ static int sock_socket_init(TALLOC_CTX *mem_ctx, const char 
*sockpath,
 
 static int sock_socket_destructor(struct sock_socket *sock)
 {
+       TALLOC_FREE(sock->req);
+
        if (sock->fd != -1) {
                close(sock->fd);
                sock->fd = -1;
@@ -331,6 +337,8 @@ static struct tevent_req *sock_socket_start_send(TALLOC_CTX 
*mem_ctx,
        }
        tevent_req_set_callback(subreq, sock_socket_start_new_client, req);
 
+       sock->req = req;
+
        return req;
 }
 
@@ -401,7 +409,8 @@ static int sock_socket_start_client_destructor(struct 
sock_client *client)
        return 0;
 }
 
-static bool sock_socket_start_recv(struct tevent_req *req, int *perr)
+static bool sock_socket_start_recv(struct tevent_req *req, int *perr,
+                                  TALLOC_CTX *mem_ctx, const char **sockpath)
 {
        struct sock_socket_start_state *state = tevent_req_data(
                req, struct sock_socket_start_state);
@@ -416,6 +425,10 @@ static bool sock_socket_start_recv(struct tevent_req *req, 
int *perr)
                return false;
        }
 
+       if (sockpath != NULL) {
+               *sockpath = talloc_steal(mem_ctx, state->sock->sockpath);
+       }
+
        return true;
 }
 
@@ -511,17 +524,24 @@ struct sock_daemon_run_state {
        pid_t pid_watch;
 
        int fd;
+       int exit_code;
 };
 
 static void sock_daemon_run_started(struct tevent_req *subreq);
+static void sock_daemon_run_startup_done(struct tevent_req *subreq);
 static void sock_daemon_run_signal_handler(struct tevent_context *ev,
                                           struct tevent_signal *se,
                                           int signum, int count, void *siginfo,
                                           void *private_data);
 static void sock_daemon_run_reconfigure(struct tevent_req *req);
+static void sock_daemon_run_reconfigure_done(struct tevent_req *subreq);
 static void sock_daemon_run_shutdown(struct tevent_req *req);
+static void sock_daemon_run_shutdown_done(struct tevent_req *subreq);
+static void sock_daemon_run_exit(struct tevent_req *req);
+static bool sock_daemon_run_socket_listen(struct tevent_req *req);
 static void sock_daemon_run_socket_fail(struct tevent_req *subreq);
 static void sock_daemon_run_watch_pid(struct tevent_req *subreq);
+static void sock_daemon_run_wait(struct tevent_req *req);
 static void sock_daemon_run_wait_done(struct tevent_req *subreq);
 
 struct tevent_req *sock_daemon_run_send(TALLOC_CTX *mem_ctx,
@@ -534,8 +554,6 @@ struct tevent_req *sock_daemon_run_send(TALLOC_CTX *mem_ctx,
        struct tevent_req *req, *subreq;
        struct sock_daemon_run_state *state;
        struct tevent_signal *se;
-       struct sock_socket *sock;
-       bool remove_before_use = false;
 
        req = tevent_req_create(mem_ctx, &state,
                                struct sock_daemon_run_state);
@@ -552,7 +570,6 @@ struct tevent_req *sock_daemon_run_send(TALLOC_CTX *mem_ctx,
                        tevent_req_error(req, EEXIST);
                        return tevent_req_post(req, ev);
                }
-               remove_before_use = true;
        }
 
        state->ev = ev;
@@ -591,18 +608,6 @@ struct tevent_req *sock_daemon_run_send(TALLOC_CTX 
*mem_ctx,
                return tevent_req_post(req, ev);
        }
 
-       for (sock = sockd->socket_list; sock != NULL; sock = sock->next) {
-               subreq = sock_socket_start_send(state, ev, sock,
-                                               remove_before_use);
-               if (tevent_req_nomem(subreq, req)) {
-                       return tevent_req_post(req, ev);
-               }
-               tevent_req_set_callback(subreq, sock_daemon_run_socket_fail,
-                                       req);
-
-               sock->req = subreq;
-       }
-
        if (pid_watch > 1) {
                subreq = tevent_wakeup_send(state, ev,
                                            tevent_timeval_current_ofs(1,0));
@@ -613,33 +618,84 @@ struct tevent_req *sock_daemon_run_send(TALLOC_CTX 
*mem_ctx,
                                        req);
        }
 
-       if (sockd->funcs != NULL && sockd->funcs->wait_send != NULL &&
-           sockd->funcs->wait_recv != NULL) {
-               subreq = sockd->funcs->wait_send(state, ev,
-                                                sockd->private_data);
+       return req;
+}
+
+static void sock_daemon_run_started(struct tevent_req *subreq)
+{
+       struct tevent_req *req = tevent_req_callback_data(
+               subreq, struct tevent_req);
+       struct sock_daemon_run_state *state = tevent_req_data(
+               req, struct sock_daemon_run_state);
+       struct sock_daemon_context *sockd = state->sockd;
+       bool status;
+
+       status = tevent_wakeup_recv(subreq);
+       TALLOC_FREE(subreq);
+       if (! status) {
+               tevent_req_error(req, EIO);
+               return;
+       }
+
+       D_NOTICE("daemon started, pid=%u\n", getpid());
+
+       if (sockd->funcs != NULL && sockd->funcs->startup_send != NULL &&
+           sockd->funcs->startup_recv != NULL) {
+               subreq = sockd->funcs->startup_send(state, state->ev,
+                                                   sockd->private_data);
                if (tevent_req_nomem(subreq, req)) {
-                       return tevent_req_post(req, ev);
+                       return;
                }
-               tevent_req_set_callback(subreq, sock_daemon_run_wait_done,
+               tevent_req_set_callback(subreq, sock_daemon_run_startup_done,
                                        req);
+               return;
        }
 
-       return req;
+       if (sockd->funcs != NULL && sockd->funcs->startup != NULL) {
+               int ret;
+
+               ret = sockd->funcs->startup(sockd->private_data);
+               if (ret != 0) {
+                       D_ERR("startup failed, ret=%d\n", ret);
+                       tevent_req_error(req, EIO);
+                       return;
+               }
+
+               D_NOTICE("startup completed successfully\n");
+       }
+
+       status = sock_daemon_run_socket_listen(req);
+       if (! status) {
+               return;
+       }
+       sock_daemon_run_wait(req);
 }
 
-static void sock_daemon_run_started(struct tevent_req *subreq)
+static void sock_daemon_run_startup_done(struct tevent_req *subreq)
 {
        struct tevent_req *req = tevent_req_callback_data(
                subreq, struct tevent_req);
        struct sock_daemon_run_state *state = tevent_req_data(
                req, struct sock_daemon_run_state);
        struct sock_daemon_context *sockd = state->sockd;
+       int ret;
+       bool status;
 
-       D_NOTICE("daemon started, pid=%u\n", getpid());
+       status = sockd->funcs->startup_recv(subreq, &ret);
+       TALLOC_FREE(subreq);
+       if (! status) {
+               D_ERR("startup failed, ret=%d\n", ret);
+               tevent_req_error(req, EIO);
+               return;
+       }
 
-       if (sockd->funcs != NULL && sockd->funcs->startup != NULL) {
-               sockd->funcs->startup(sockd->private_data);
+       D_NOTICE("startup completed succesfully\n");
+
+       status = sock_daemon_run_socket_listen(req);
+       if (! status) {
+               return;
        }
+       sock_daemon_run_wait(req);
 }
 
 static void sock_daemon_run_signal_handler(struct tevent_context *ev,
@@ -649,6 +705,8 @@ static void sock_daemon_run_signal_handler(struct 
tevent_context *ev,
 {
        struct tevent_req *req = talloc_get_type_abort(
                private_data, struct tevent_req);
+       struct sock_daemon_run_state *state = tevent_req_data(
+               req, struct sock_daemon_run_state);
 
        D_NOTICE("Received signal %d\n", signum);
 
@@ -658,24 +716,66 @@ static void sock_daemon_run_signal_handler(struct 
tevent_context *ev,
        }
 
        if (signum == SIGINT || signum == SIGTERM) {
+               state->exit_code = EINTR;
                sock_daemon_run_shutdown(req);
-               tevent_req_error(req, EINTR);
        }
 }
 
 static void sock_daemon_run_reconfigure(struct tevent_req *req)
 {
+       struct tevent_req *subreq;
        struct sock_daemon_run_state *state = tevent_req_data(
                req, struct sock_daemon_run_state);
        struct sock_daemon_context *sockd = state->sockd;
 
+       if (sockd->funcs != NULL && sockd->funcs->reconfigure_send != NULL &&
+           sockd->funcs->reconfigure_recv != NULL) {
+               subreq = sockd->funcs->reconfigure_send(state, state->ev,
+                                                       sockd->private_data);
+               if (tevent_req_nomem(subreq, req)) {
+                       return;
+               }
+               tevent_req_set_callback(subreq,
+                                       sock_daemon_run_reconfigure_done, req);
+               return;
+       }
+
        if (sockd->funcs != NULL && sockd->funcs->reconfigure != NULL) {
-               sockd->funcs->reconfigure(sockd->private_data);
+               int ret;
+
+               ret = sockd->funcs->reconfigure(sockd->private_data);
+               if (ret != 0) {
+                       D_ERR("reconfigure failed, ret=%d\n", ret);
+                       return;
+               }
+
+               D_NOTICE("reconfigure completed successfully\n");
+       }
+}
+
+static void sock_daemon_run_reconfigure_done(struct tevent_req *subreq)
+{
+       struct tevent_req *req = tevent_req_callback_data(
+               subreq, struct tevent_req);
+       struct sock_daemon_run_state *state = tevent_req_data(
+               req, struct sock_daemon_run_state);
+       struct sock_daemon_context *sockd = state->sockd;
+       int ret;
+       bool status;
+
+       status = sockd->funcs->reconfigure_recv(subreq, &ret);
+       TALLOC_FREE(subreq);
+       if (! status) {
+               D_ERR("reconfigure failed, ret=%d\n", ret);
+               return;
        }
+
+       D_NOTICE("reconfigure completed successfully\n");
 }
 
 static void sock_daemon_run_shutdown(struct tevent_req *req)
 {
+       struct tevent_req *subreq;
        struct sock_daemon_run_state *state = tevent_req_data(
                req, struct sock_daemon_run_state);
        struct sock_daemon_context *sockd = state->sockd;
@@ -685,32 +785,103 @@ static void sock_daemon_run_shutdown(struct tevent_req 
*req)
 
        while ((sock = sockd->socket_list) != NULL) {
                DLIST_REMOVE(sockd->socket_list, sock);
-               TALLOC_FREE(sock->req);
                TALLOC_FREE(sock);
        }
 
+       if (sockd->funcs != NULL && sockd->funcs->shutdown_send != NULL &&
+           sockd->funcs->shutdown_recv != NULL) {
+               subreq = sockd->funcs->shutdown_send(state, state->ev,
+                                                    sockd->private_data);
+               if (subreq == NULL) {
+                       sock_daemon_run_exit(req);
+                       return;
+               }
+               tevent_req_set_callback(subreq, sock_daemon_run_shutdown_done,
+                                               req);
+               return;
+       }
+
        if (sockd->funcs != NULL && sockd->funcs->shutdown != NULL) {
                sockd->funcs->shutdown(sockd->private_data);
        }
 
+       sock_daemon_run_exit(req);
+}
+
+static void sock_daemon_run_shutdown_done(struct tevent_req *subreq)
+{
+       struct tevent_req *req = tevent_req_callback_data(
+               subreq, struct tevent_req);
+       struct sock_daemon_run_state *state = tevent_req_data(
+               req, struct sock_daemon_run_state);
+       struct sock_daemon_context *sockd = state->sockd;
+
+       sockd->funcs->shutdown_recv(subreq);
+       TALLOC_FREE(subreq);
+
+       sock_daemon_run_exit(req);
+}
+
+static void sock_daemon_run_exit(struct tevent_req *req)
+{
+       struct sock_daemon_run_state *state = tevent_req_data(
+               req, struct sock_daemon_run_state);
+       struct sock_daemon_context *sockd = state->sockd;
+
        TALLOC_FREE(sockd->pid_ctx);
+
+       if (state->exit_code == 0) {
+               tevent_req_done(req);
+       } else {
+               tevent_req_error(req, state->exit_code);
+       }
+}
+
+static bool sock_daemon_run_socket_listen(struct tevent_req *req)
+{
+       struct tevent_req *subreq;
+       struct sock_daemon_run_state *state = tevent_req_data(
+               req, struct sock_daemon_run_state);
+       struct sock_daemon_context *sockd = state->sockd;
+       struct sock_socket *sock;
+       bool remove_before_use = false;
+
+       if (sockd->pid_ctx != NULL) {
+               remove_before_use = true;
+       }
+       for (sock = sockd->socket_list; sock != NULL; sock = sock->next) {
+               subreq = sock_socket_start_send(state, state->ev, sock,
+                                               remove_before_use);
+               if (tevent_req_nomem(subreq, req)) {
+                       return false;
+               }
+               tevent_req_set_callback(subreq, sock_daemon_run_socket_fail,
+                                       req);
+       }
+
+       return true;
 }
 
 static void sock_daemon_run_socket_fail(struct tevent_req *subreq)
 {
        struct tevent_req *req = tevent_req_callback_data(
                subreq, struct tevent_req);
+       struct sock_daemon_run_state *state = tevent_req_data(
+               req, struct sock_daemon_run_state);
+       const char *sockpath = NULL;
        int ret = 0;
        bool status;
 
-       status = sock_socket_start_recv(subreq, &ret);
+       status = sock_socket_start_recv(subreq, &ret, state, &sockpath);
        TALLOC_FREE(subreq);
-       sock_daemon_run_shutdown(req);
        if (! status) {
-               tevent_req_error(req, ret);
+               D_ERR("socket %s closed unexpectedly\n", sockpath);
+               state->exit_code = ret;
        } else {
-               tevent_req_done(req);
+               state->exit_code = 0;
        }
+
+       sock_daemon_run_shutdown(req);
 }
 
 static void sock_daemon_run_watch_pid(struct tevent_req *subreq)
@@ -733,8 +904,8 @@ static void sock_daemon_run_watch_pid(struct tevent_req 
*subreq)
        if (ret == -1) {
                if (errno == ESRCH) {
                        D_ERR("PID %d gone away, exiting\n", state->pid_watch);
+                       state->exit_code = ESRCH;
                        sock_daemon_run_shutdown(req);
-                       tevent_req_error(req, ESRCH);
                        return;
                } else {
                        D_ERR("Failed to check PID status %d, ret=%d\n",
@@ -750,6 +921,25 @@ static void sock_daemon_run_watch_pid(struct tevent_req 
*subreq)
        tevent_req_set_callback(subreq, sock_daemon_run_watch_pid, req);
 }
 
+static void sock_daemon_run_wait(struct tevent_req *req)
+{
+       struct tevent_req *subreq;
+       struct sock_daemon_run_state *state = tevent_req_data(
+               req, struct sock_daemon_run_state);
+       struct sock_daemon_context *sockd = state->sockd;
+
+       if (sockd->funcs != NULL && sockd->funcs->wait_send != NULL &&
+           sockd->funcs->wait_recv != NULL) {
+               subreq = sockd->funcs->wait_send(state, state->ev,
+                                                sockd->private_data);
+               if (tevent_req_nomem(subreq, req)) {
+                       return;
+               }
+               tevent_req_set_callback(subreq, sock_daemon_run_wait_done,
+                                       req);
+       }
+}
+
 static void sock_daemon_run_wait_done(struct tevent_req *subreq)
 {
        struct tevent_req *req = tevent_req_callback_data(
@@ -757,17 +947,18 @@ static void sock_daemon_run_wait_done(struct tevent_req 
*subreq)
        struct sock_daemon_run_state *state = tevent_req_data(
                req, struct sock_daemon_run_state);
        struct sock_daemon_context *sockd = state->sockd;
-       int ret;
+       int ret = 0;
        bool status;
 
        status = sockd->funcs->wait_recv(subreq, &ret);
        TALLOC_FREE(subreq);
-       sock_daemon_run_shutdown(req);
        if (! status) {
-               tevent_req_error(req, ret);
+               state->exit_code = ret;
        } else {
-               tevent_req_done(req);
+               state->exit_code = 0;
        }
+
+       sock_daemon_run_shutdown(req);
 }
 
 bool sock_daemon_run_recv(struct tevent_req *req, int *perr)
diff --git a/ctdb/common/sock_daemon.h b/ctdb/common/sock_daemon.h
index 1821028..a071833 100644
--- a/ctdb/common/sock_daemon.h
+++ b/ctdb/common/sock_daemon.h
@@ -48,11 +48,27 @@ struct sock_client_context;
  * @brief The callback routines called during daemon life cycle
  *
  * startup() is called when the daemon starts running
- *            either via sock_daemon_run() or via sock_daemon_run_send()
- * reconfigure() is called when process receives SIGUSR1 or SIGHUP
+ *     either via sock_daemon_run() or via sock_daemon_run_send()
+ *     startup() should return 0 for success, non-zero value on failure
+ *     On failure, sock_daemon_run() will return error.
+ *
+ * startup_send()/startup_recv() is the async version of startup()
+ *
+ * reconfigure() is called when the daemon receives SIGUSR1 or SIGHUP
+ *     reconfigure() should return 0 for success, non-zero value on failure
+ *     On failure, sock_daemon_run() will continue to run.
+ *
+ * reconfigure_send()/reconfigure_recv() is the async version of reconfigure()
+ *
  * shutdown() is called when process receives SIGINT or SIGTERM or
  *             when wait computation has finished
  *
+ * shutdown_send()/shutdown_recv() is the async version of shutdown()
+ *
+ * Please note that only one (sync or async) version of these functions
+ * will be called.  If both versions are defined, then only async function
+ * will be called.
+ *
  * wait_send() starts the async computation to keep running the daemon
  * wait_recv() ends the async computation to keep running the daemon
  *
@@ -60,10 +76,27 @@ struct sock_client_context;
  * If wait_send() returns req, then when req is over, daemon will shutdown.
  */
 struct sock_daemon_funcs {
-       void (*startup)(void *private_data);
-       void (*reconfigure)(void *private_data);
+       int (*startup)(void *private_data);


-- 
Samba Shared Repository

Reply via email to