]> arthur.barton.de Git - netdata.git/commitdiff
fix for defunct childs
authorCosta Tsaousis (ktsaou) <costa@tsaousis.gr>
Tue, 5 May 2015 20:01:14 +0000 (23:01 +0300)
committerCosta Tsaousis (ktsaou) <costa@tsaousis.gr>
Tue, 5 May 2015 20:01:14 +0000 (23:01 +0300)
src/daemon.c
src/main.c
src/plugin_tc.c
src/plugins_d.c
src/popen.c
src/popen.h
web/index.js

index 2b66aa042fedab01bad7c3930cdb785aa6e121dc..e40040f6c6d5a931ff24860f879536a44c185ef7 100755 (executable)
@@ -37,8 +37,8 @@ void sig_handler(int signo)
                        signal(SIGQUIT, SIG_IGN);
                        signal(SIGHUP,  SIG_IGN);
                        signal(SIGINT,  SIG_IGN);
+                       signal(SIGCHLD, SIG_IGN);
                        kill_childs();
-                       process_childs(0);
                        rrdset_free_all();
                        //unlink("/var/run/netdata.pid");
                        info("NetData exiting. Bye bye...");
@@ -51,12 +51,6 @@ void sig_handler(int signo)
                        // info("Ignoring signal %d. Errno: %d (%s)", signo, errno, strerror(errno));
                        break;
 
-
-               case SIGCHLD:
-                       info("Received SIGCHLD (signal %d).", signo);
-                       process_childs(0);
-                       break;
-
                default:
                        info("Signal %d received. Falling back to default action for it.", signo);
                        signal(signo, SIG_DFL);
@@ -200,8 +194,8 @@ int become_daemon(int close_all_files, const char *input, const char *output, co
        if (setsid() < 0)
                exit(2);
 
-       signal(SIGCHLD, SIG_IGN);
-       signal(SIGHUP, SIG_IGN);
+       signal(SIGCHLD,  SIG_IGN);
+       signal(SIGHUP,   SIG_IGN);
        signal(SIGWINCH, SIG_IGN);
 
        // fork() again
index 6b11ab6b7853a60a82f7e96674c06e57211b0729..68ac66c1b32bf272d317430559e6c9beea83113b 100755 (executable)
@@ -316,8 +316,20 @@ int main(int argc, char **argv)
 
 
        // catch all signals
-       for (i = 1 ; i < 65 ;i++) if(i != SIGSEGV && i != SIGFPE) signal(i,  sig_handler);
-       
+       for (i = 1 ; i < 65 ;i++) {
+               switch(i) {
+                       case SIGSEGV:
+                       case SIGFPE:
+                       case SIGCHLD:
+                               signal(i, SIG_DFL);
+                               break;
+
+                       default:
+                               signal(i,  sig_handler);
+                               break;
+               }
+       }
+
        for (i = 0; static_threads[i].name != NULL ; i++) {
                struct netdata_static_thread *st = &static_threads[i];
 
@@ -335,13 +347,8 @@ int main(int argc, char **argv)
                else info("Not starting thread %s.", st->name);
        }
 
-       // the main process - the web server listener
-       // this never ends
-       // socket_listen_main(NULL);
-       while(1) {
-               process_childs(1);
-               sleep(1);
-       }
+       // for future use - the main thread
+       while(1) sleep(60);
 
        exit(0);
 }
index 708da0192e8d003d5c89f6cb53fbf96ddfbf6e28..3f6665a945a901af9a216b94ba880c62deda0876 100755 (executable)
@@ -580,7 +580,8 @@ void *tc_main(void *ptr)
                        //      debug(D_TC_LOOP, "IGNORED line");
                        //}
                }
-               mypclose(fp);
+               mypclose(fp, tc_child_pid);
+               tc_child_pid = 0;
 
                if(device) {
                        // tc_device_free(device);
index c39266c4c77f30356b21f98beb85e1f6aa270d9f..1bc567752b488cc765206bc95429bd4ea36a846f 100755 (executable)
@@ -366,7 +366,8 @@ void *pluginsd_worker_thread(void *arg)
                }
 
                // fgets() failed or loop broke
-               mypclose(fp);
+               mypclose(fp, cd->pid);
+               cd->pid = 0;
 
                if(!count && cd->enabled) {
                        error("PLUGINSD: '%s' does not generate usefull output. Disabling it.", cd->fullfilename);
index ab064d48d95ad09c90ed10d3cb43032bb3113e39..279373b49f78baf88f4bf940afa7d292f56f1a13 100755 (executable)
@@ -6,7 +6,46 @@
 
 #include "log.h"
 #include "popen.h"
+/*
+struct mypopen {
+       pid_t pid;
+       FILE *fp;
+       struct mypopen *next;
+       struct mypopen *prev;
+};
+
+static struct mypopen *mypopen_root = NULL;
+
+static void mypopen_add(FILE *fp, pid_t *pid) {
+       struct mypopen *mp = malloc(sizeof(struct mypopen));
+       if(!mp) {
+               fatal("Cannot allocate %zu bytes", sizeof(struct mypopen))
+               return;
+       }
+
+       mp->fp = fp;
+       mp->pid = pid;
+       mp->next = popen_root;
+       mp->prev = NULL;
+       if(mypopen_root) mypopen_root->prev = mp;
+       mypopen_root = mp;
+}
+
+static void mypopen_del(FILE *fp) {
+       struct mypopen *mp;
 
+       for(mp = mypopen_root; mp; mp = mp->next)
+               if(mp->fd == fp) break;
+
+       if(!mp) error("Cannot find mypopen() file pointer in open childs.");
+       else {
+               if(mp->next) mp->next->prev = mp->prev;
+               if(mp->prev) mp->prev->next = mp->next;
+               if(mypopen_root == mp) mypopen_root = mp->next;
+               free(mp);
+       }
+}
+*/
 #define PIPE_READ 0
 #define PIPE_WRITE 1
 
@@ -27,6 +66,7 @@ FILE *mypopen(const char *command, pid_t *pidptr)
                *pidptr = pid;
                close(pipefd[PIPE_WRITE]);
                FILE *fp = fdopen(pipefd[PIPE_READ], "r");
+               /*mypopen_add(fp, pid);*/
                return(fp);
        }
        // the child
@@ -68,7 +108,7 @@ FILE *mypopen(const char *command, pid_t *pidptr)
        fflush(NULL);
 #endif
        
-       // ignore all signals
+       // reset all signals
        for (i = 1 ; i < 65 ;i++) if(i != SIGSEGV) signal(i, SIG_DFL);
 
        fprintf(stderr, "executing command: '%s' on pid %d.\n", command, getpid());
@@ -76,24 +116,12 @@ FILE *mypopen(const char *command, pid_t *pidptr)
        exit(1);
 }
 
-void mypclose(FILE *fp)
-{
-       // this is a very poor implementation of pclose()
-       // the caller should catch SIGCHLD and waitpid() on the exited child
-       // otherwise the child will be a zombie forever
-
+void mypclose(FILE *fp, pid_t pid) {
+       /*mypopen_del(fp);*/
        fclose(fp);
-}
 
-void process_childs(int wait)
-{
        siginfo_t info;
-       int options = WEXITED;
-       if(!wait) options |= WNOHANG;
-
-       info.si_pid = 0;
-       while(waitid(P_ALL, 0, &info, options) == 0) {
-               if(!info.si_pid) break;
+       if(waitid(P_PID, pid, &info, WEXITED) != -1) {
                switch(info.si_code) {
                        case CLD_EXITED:
                                error("pid %d exited with code %d.", info.si_pid, info.si_status);
@@ -123,8 +151,6 @@ void process_childs(int wait)
                                error("pid %d gave us a SIGCHLD with code %d and status %d.", info.si_pid, info.si_code, info.si_status);
                                break;
                }
-
-               // prevent an infinite loop
-               info.si_pid = 0;
        }
+       else error("Cannot waitid() for pid %d", pid);
 }
index f2ef866a156bdec647a982e2bec28d024e68d5c9..2f0069426395776931fd776eb5a6becf3f611aff 100755 (executable)
@@ -9,7 +9,6 @@
 #define PIPE_WRITE 1
 
 extern FILE *mypopen(const char *command, pid_t *pidptr);
-extern void mypclose(FILE *fp);
-extern void process_childs(int wait);
+extern void mypclose(FILE *fp, pid_t pid);
 
 #endif /* NETDATA_POPEN_H */
index fc376e5396ccf3c837435665dbde5ae5313eb170..ea248eb0ff60306323422b6b9e9659468ceb2de3 100755 (executable)
@@ -4,13 +4,13 @@ var TARGET_THUMB_GRAPH_WIDTH = 500;           // thumb charts width will range from 0.5 t
 var MINIMUM_THUMB_GRAPH_WIDTH = 400;   // thumb chart will generally try to be wider than that
 var TARGET_THUMB_GRAPH_HEIGHT = 180;   // the height of the thumb charts
 
-var THUMBS_MAX_TIME_TO_SHOW = 600;             // how much time the thumb charts will present?
-var THUMBS_POINTS_DIVISOR = 4;
-var THUMBS_STACKED_POINTS_DIVISOR = 10;
+var THUMBS_MAX_TIME_TO_SHOW = 240;             // how much time the thumb charts will present?
+var THUMBS_POINTS_DIVISOR = 3;
+var THUMBS_STACKED_POINTS_DIVISOR = 3;
 
-var GROUPS_MAX_TIME_TO_SHOW = 600;             // how much time the thumb charts will present?
-var GROUPS_POINTS_DIVISOR = 4;
-var GROUPS_STACKED_POINTS_DIVISOR = 10;
+var GROUPS_MAX_TIME_TO_SHOW = 120;             // how much time the thumb charts will present?
+var GROUPS_POINTS_DIVISOR = 2;
+var GROUPS_STACKED_POINTS_DIVISOR = 2;
 
 var MAINCHART_MAX_TIME_TO_SHOW = 600;  // how much time the main chart will present by default?
 var MAINCHART_POINTS_DIVISOR = 5;              // how much detailed will the main chart be by default? 1 = finest, higher is faster