]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
MINOR: mworker: don't use children variable anymore
authorWilliam Lallemand <wlallemand@haproxy.com>
Mon, 1 Apr 2019 09:29:59 +0000 (11:29 +0200)
committerWilly Tarreau <w@1wt.eu>
Mon, 1 Apr 2019 12:45:37 +0000 (14:45 +0200)
The children variable is still used in haproxy, it is not required
anymore since we have the information about the current workers in the
mworker_proc linked list.

The oldpids array is also replaced by this linked list when we
generated the arguments for the master reexec.

include/proto/mworker.h
src/haproxy.c
src/mworker.c

index 3b3e28066f0778c208d6fcf17d833d9ea7c14fcc..02a10deab277f4f8a2cc66afba6ae75fbe01f5d7 100644 (file)
@@ -31,6 +31,7 @@ void mworker_pipe_register();
 
 void mworker_cleanlisteners();
 
-extern int *children; /* store PIDs of children in master workers mode */
+int mworker_child_nb();
+
 
 #endif /* PROTO_MWORKER_H_ */
index 77efdd50c9c717fe4642592fe83de28064143b92..b2bf558bb0840fcfb4685fe328982dab3d8dfc3e 100644 (file)
@@ -557,7 +557,6 @@ static void get_cur_unixsocket()
 void mworker_reload()
 {
        int next_argc = 0;
-       int j;
        char *msg = NULL;
        struct rlimit limit;
        struct per_thread_deinit_fct *ptdf;
@@ -598,29 +597,27 @@ void mworker_reload()
                next_argc++;
 
        /* 1 for haproxy -sf, 2 for -x /socket */
-       next_argv = realloc(next_argv, (next_argc + 1 + 2 + global.nbproc + nb_oldpids + 1) * sizeof(char *));
+       next_argv = realloc(next_argv, (next_argc + 1 + 2 + mworker_child_nb() + nb_oldpids + 1) * sizeof(char *));
        if (next_argv == NULL)
                goto alloc_error;
 
-
        /* add -sf <PID>*  to argv */
-       if (children || nb_oldpids > 0)
+       if (mworker_child_nb() > 0) {
+               struct mworker_proc *child;
+
                next_argv[next_argc++] = "-sf";
-       if (children) {
-               for (j = 0; j < global.nbproc; next_argc++,j++) {
-                       next_argv[next_argc] = memprintf(&msg, "%d", children[j]);
+
+               list_for_each_entry(child, &proc_list, list) {
+                       if (child->type != 'w' && child->type != 'e')
+                               continue;
+                       next_argv[next_argc] = memprintf(&msg, "%d", child->pid);
                        if (next_argv[next_argc] == NULL)
                                goto alloc_error;
                        msg = NULL;
+                       next_argc++;
                }
        }
-       /* copy old process PIDs */
-       for (j = 0; j < nb_oldpids; next_argc++,j++) {
-               next_argv[next_argc] = memprintf(&msg, "%d", oldpids[j]);
-               if (next_argv[next_argc] == NULL)
-                       goto alloc_error;
-               msg = NULL;
-       }
+
        next_argv[next_argc] = NULL;
 
        /* add the -x option with the stat socket */
@@ -2844,7 +2841,6 @@ int main(int argc, char **argv)
 
                /* the father launches the required number of processes */
                if (!(global.mode & MODE_MWORKER_WAIT)) {
-                       children = calloc(global.nbproc, sizeof(int));
                        for (proc = 0; proc < global.nbproc; proc++) {
                                ret = fork();
                                if (ret < 0) {
@@ -2854,7 +2850,6 @@ int main(int argc, char **argv)
                                }
                                else if (ret == 0) /* child breaks here */
                                        break;
-                               children[proc] = ret;
                                if (pidfd >= 0 && !(global.mode & MODE_MWORKER)) {
                                        char pidstr[100];
                                        snprintf(pidstr, sizeof(pidstr), "%d\n", ret);
index 0d46884f08ff01ec659cea36e0908099c7b63fff..0c4ae21b270110f5e1ef3cfbeca02a0a9cccc84e 100644 (file)
@@ -36,8 +36,6 @@
 
 static int exitcode = -1;
 
-int *children = NULL; /* store PIDs of children in master workers mode */
-
 /* ----- children processes handling ----- */
 
 /*
@@ -46,29 +44,46 @@ int *children = NULL; /* store PIDs of children in master workers mode */
 
 static void mworker_kill(int sig)
 {
-       int i;
+       struct mworker_proc *child;
 
-       /* TODO: merge mworker_kill and tell_old_pids for mworker mode */
-       tell_old_pids(sig);
-       if (children) {
-               for (i = 0; i < global.nbproc; i++)
-                       kill(children[i], sig);
+       list_for_each_entry(child, &proc_list, list) {
+               /* careful there, we must be sure that the pid > 0, we don't want to emit a kill -1 */
+               if ((child->type == 'w' || child->type == 'e') && (child->reloads == 0) && (child->pid > 0))
+                       kill(child->pid, sig);
        }
 }
 
 
 /* return 1 if a pid is a current child otherwise 0 */
-int current_child(int pid)
+int mworker_current_child(int pid)
 {
-       int i;
+       struct mworker_proc *child;
 
-       for (i = 0; i < global.nbproc; i++) {
-               if (children[i] == pid)
+       list_for_each_entry(child, &proc_list, list) {
+               if ((child->type == 'w' || child->type == 'e') && (child->reloads == 0) && (child->pid == pid))
                        return 1;
        }
        return 0;
 }
 
+/*
+ * Return the number of new and old children (including workers and external
+ * processes)
+ */
+int mworker_child_nb()
+{
+       struct mworker_proc *child;
+       int ret = 0;
+
+       list_for_each_entry(child, &proc_list, list) {
+               if ((child->type == 'w' || child->type == 'e'))
+                       ret++;
+       }
+
+       return ret;
+}
+
+
 /*
  * serialize the proc list and put it in the environment
  */
@@ -204,6 +219,7 @@ restart_wait:
                else
                        status = 255;
 
+               /* delete the child from the process list */
                list_for_each_entry_safe(child, it, &proc_list, list) {
                        if (child->pid != exitpid)
                                continue;
@@ -214,12 +230,15 @@ restart_wait:
                        break;
                }
 
-               if (!children || !childfound) {
+               if (!childfound) {
+                       /* We didn't find the PID in the list, that shouldn't happen but we can emit a warning */
                        ha_warning("Worker %d exited with code %d (%s)\n", exitpid, status, (status >= 128) ? strsignal(status - 128) : "Exit");
                } else {
-                       /* check if exited child was in the current children list */
-                       if (current_child(exitpid)) {
-                               ha_alert("Current worker #%d (%d) exited with code %d (%s)\n", child->relative_pid, exitpid, status, (status >= 128) ? strsignal(status - 128) : "Exit");
+                       /* check if exited child was is a current child */
+                       if (child->reloads == 0) {
+                               if (child->type == 'w')
+                                       ha_alert("Current worker #%d (%d) exited with code %d (%s)\n", child->relative_pid, exitpid, status, (status >= 128) ? strsignal(status - 128) : "Exit");
+
                                if (status != 0 && status != 130 && status != 143
                                    && !(global.tune.options & GTUNE_NOEXIT_ONFAILURE)) {
                                        ha_alert("exit-on-failure: killing every workers with SIGTERM\n");
@@ -228,9 +247,10 @@ restart_wait:
                                        mworker_kill(SIGTERM);
                                }
                        } else {
-                               ha_warning("Former worker #%d (%d) exited with code %d (%s)\n", child->relative_pid, exitpid, status, (status >= 128) ? strsignal(status - 128) : "Exit");
-                               /* TODO: merge children and oldpids list in mworker mode */
-                               delete_oldpid(exitpid);
+                               if (child->type == 'w') {
+                                       ha_warning("Former worker #%d (%d) exited with code %d (%s)\n", child->relative_pid, exitpid, status, (status >= 128) ? strsignal(status - 128) : "Exit");
+                                       delete_oldpid(exitpid);
+                               }
                        }
                        free(child);
                }