]> arthur.barton.de Git - netdata.git/commitdiff
added more error exit tracing info to trace issue 529; switched to accept4() and...
authorCosta Tsaousis (ktsaou) <costa@tsaousis.gr>
Fri, 10 Jun 2016 20:16:35 +0000 (23:16 +0300)
committerCosta Tsaousis (ktsaou) <costa@tsaousis.gr>
Fri, 10 Jun 2016 20:16:35 +0000 (23:16 +0300)
configure.ac
src/daemon.c
src/log.h
src/main.c
src/popen.c
src/rrd.c
src/web_client.c
src/web_server.c
src/web_server.h

index 240725c1edd8756179da5bd585f88f9bef7a9419..d2ee0e645b59097763143cb21bdf7adfbb2cb2e5 100644 (file)
@@ -34,6 +34,7 @@ AC_PROG_CC
 AC_PROG_INSTALL
 PKG_PROG_PKG_CONFIG
 AC_USE_SYSTEM_EXTENSIONS
+AC_CHECK_FUNCS_ONCE(accept4)
 
 AC_ARG_ENABLE(
        [plugin-nfacct],
index 4b7af3c2e772cc720b93da7736dae2d35c838201..82b763295ca0be0763c3ecf3aa0def46ebd1b2c1 100644 (file)
@@ -29,8 +29,11 @@ char pidfile[FILENAME_MAX + 1] = "";
 
 void sig_handler(int signo)
 {
-       if(signo)
+       if(signo) {
+               error_log_limit_unlimited();
+               error("Received signal %d. Exiting...", signo);
                netdata_exit = 1;
+       }
 }
 
 static void properly_chown_netdata_generated_file(int fd, uid_t uid, gid_t gid) {
index 3f811d9fbe93bf3160a14049590b0ceb8356607f..4d441e8f6ade6913dc2d7d97d6413d8834d1d7f5 100644 (file)
--- a/src/log.h
+++ b/src/log.h
@@ -50,6 +50,7 @@ extern unsigned long error_log_errors_per_period;
 extern int error_log_limit(int reset);
 
 #define error_log_limit_reset() do { error_log_limit(1); } while(0)
+#define error_log_limit_unlimited() do { error_log_throttle_period = 0; } while(0)
 
 #define debug(type, args...) do { if(unlikely(!silent && (debug_flags & type))) debug_int(__FILE__, __FUNCTION__, __LINE__, ##args); } while(0)
 #define info(args...)    info_int(__FILE__, __FUNCTION__, __LINE__, ##args)
index 312dab6efd64a44d5bebc19a3543423391b91649..f784592cdcebdb7cf74999a79c0a44261df6cc76 100644 (file)
@@ -40,15 +40,15 @@ extern void *cgroups_main(void *ptr);
 
 volatile sig_atomic_t netdata_exit = 0;
 
-void netdata_cleanup_and_exit(int ret)
-{
+void netdata_cleanup_and_exit(int ret) {
        netdata_exit = 1;
+
+       error_log_limit_unlimited();
+
+       info("Called: netdata_cleanup_and_exit()");
        rrdset_save_all();
        // kill_childs();
 
-       // let it log a few more error messages
-       error_log_limit_reset();
-
        if(pidfile[0]) {
                if(unlink(pidfile) != 0)
                        error("Cannot unlink pidfile '%s'.", pidfile);
index 06f27c0b7c4c6ec69a5a4342145137a436cdc98a..1c311d6a4fa81277e42d963b4a02f5cf17e3a2b0 100644 (file)
@@ -93,7 +93,9 @@ FILE *mypopen(const char *command, pid_t *pidptr)
 
        // fork again to become session leader
        pid = fork();
-       if(pid == -1) fprintf(stderr, "Cannot fork again on pid %d\n", getpid());
+       if(pid == -1)
+               error("pre-execution of command '%s' on pid %d: Cannot fork 2nd time.", command, getpid());
+
        if(pid != 0) {
                // the parent
                exit(0);
@@ -101,13 +103,13 @@ FILE *mypopen(const char *command, pid_t *pidptr)
 
        // set a new process group id for just this child
        if( setpgid(0, 0) != 0 )
-               error("Cannot set a new process group for pid %d (%s)", getpid(), strerror(errno));
+               error("pre-execution of command '%s' on pid %d: Cannot set a new process group.", command, getpid());
 
        if( getpgid(0) != getpid() )
-               error("Process group set is incorrect. Expected %d, found %d", getpid(), getpgid(0));
+               error("pre-execution of command '%s' on pid %d: Cannot set a new process group. Process group set is incorrect. Expected %d, found %d", command, getpid(), getpid(), getpgid(0));
 
        if( setsid() != 0 )
-               error("Cannot set session id for pid %d (%s)", getpid(), strerror(errno));
+               error("pre-execution of command '%s' on pid %d: Cannot set session id.", command, getpid());
 
        fprintf(stdout, "MYPID %d\n", getpid());
        fflush(NULL);
@@ -118,18 +120,17 @@ FILE *mypopen(const char *command, pid_t *pidptr)
                sigset_t sigset;
                sigfillset(&sigset);
 
-               if(pthread_sigmask(SIG_UNBLOCK, &sigset, NULL) == -1) {
-                       error("Could not block signals for threads");
-               }
+               if(pthread_sigmask(SIG_UNBLOCK, &sigset, NULL) == -1)
+                       error("pre-execution of command '%s' on pid %d: could not unblock signals for threads.", command, getpid());
+               
                // We only need to reset ignored signals.
                // Signals with signal handlers are reset by default.
                struct sigaction sa;
                sigemptyset(&sa.sa_mask);
                sa.sa_handler = SIG_DFL;
                sa.sa_flags = 0;
-               if(sigaction(SIGPIPE, &sa, NULL) == -1) {
-                       error("Failed to change signal handler for SIGTERM");
-               }
+               if(sigaction(SIGPIPE, &sa, NULL) == -1)
+                       error("pre-execution of command '%s' on pid %d: failed to set default signal handler for SIGPIPE.", command, getpid());
        }
 
 
@@ -148,41 +149,43 @@ int mypclose(FILE *fp, pid_t pid) {
        if(waitid(P_PID, (id_t) pid, &info, WEXITED) != -1) {
                switch(info.si_code) {
                        case CLD_EXITED:
-                               error("pid %d exited with code %d.", info.si_pid, info.si_status);
+                               error("child pid %d exited with code %d.", info.si_pid, info.si_status);
                                return(info.si_status);
                                break;
 
                        case CLD_KILLED:
-                               error("pid %d killed by signal %d.", info.si_pid, info.si_status);
+                               error("child pid %d killed by signal %d.", info.si_pid, info.si_status);
                                return(-1);
                                break;
 
                        case CLD_DUMPED:
-                               error("pid %d core dumped by signal %d.", info.si_pid, info.si_status);
+                               error("child pid %d core dumped by signal %d.", info.si_pid, info.si_status);
                                return(-2);
                                break;
 
                        case CLD_STOPPED:
-                               error("pid %d stopped by signal %d.", info.si_pid, info.si_status);
+                               error("child pid %d stopped by signal %d.", info.si_pid, info.si_status);
                                return(0);
                                break;
 
                        case CLD_TRAPPED:
-                               error("pid %d trapped by signal %d.", info.si_pid, info.si_status);
+                               error("child pid %d trapped by signal %d.", info.si_pid, info.si_status);
                                return(-4);
                                break;
 
                        case CLD_CONTINUED:
-                               error("pid %d continued by signal %d.", info.si_pid, info.si_status);
+                               error("child pid %d continued by signal %d.", info.si_pid, info.si_status);
                                return(0);
                                break;
 
                        default:
-                               error("pid %d gave us a SIGCHLD with code %d and status %d.", info.si_pid, info.si_code, info.si_status);
+                               error("child pid %d gave us a SIGCHLD with code %d and status %d.", info.si_pid, info.si_code, info.si_status);
                                return(-5);
                                break;
                }
        }
-       else error("Cannot waitid() for pid %d", pid);
+       else
+               error("Cannot waitid() for pid %d", pid);
+       
        return 0;
 }
index 0d1bed54b4babd8a3e8b1fc1b8838713e6976439..2a134fc2a8178dbe4d4e9858e64d56547e08c69c 100644 (file)
--- a/src/rrd.c
+++ b/src/rrd.c
@@ -661,12 +661,8 @@ void rrdset_free_all(void)
        info("Memory cleanup completed...");
 }
 
-void rrdset_save_all(void)
-{
-       debug(D_RRD_CALLS, "rrdset_save_all()");
-
-       // let it log a few error messages
-       error_log_limit_reset();
+void rrdset_save_all(void) {
+       info("Saving database...");
 
        RRDSET *st;
        RRDDIM *rd;
index 30fdf3851f4b322d28e84967435a1a5dfe840227..4fe40700ee27d28782808d2c1480e3decc2bf67b 100644 (file)
@@ -22,6 +22,7 @@
 
 #include "common.h"
 #include "log.h"
+#include "main.h"
 #include "appconfig.h"
 #include "url.h"
 #include "web_buffer.h"
@@ -44,8 +45,6 @@ int web_donotrack_comply = 0;
 int web_enable_gzip = 1, web_gzip_level = 3, web_gzip_strategy = Z_DEFAULT_STRATEGY;
 #endif /* NETDATA_WITH_ZLIB */
 
-extern int netdata_exit;
-
 struct web_client *web_clients = NULL;
 unsigned long long web_clients_count = 0;
 
@@ -99,7 +98,7 @@ struct web_client *web_client_create(int listener)
                sadr = (struct sockaddr*) &w->clientaddr;
                addrlen = sizeof(w->clientaddr);
 
-               w->ifd = accept(listener, sadr, &addrlen);
+               w->ifd = accept4(listener, sadr, &addrlen, SOCK_NONBLOCK);
                if (w->ifd == -1) {
                        error("%llu: Cannot accept new incoming connection.", w->id);
                        free(w);
@@ -141,8 +140,6 @@ struct web_client *web_client_create(int listener)
                flag = 1;
                if(setsockopt(w->ifd, SOL_SOCKET, SO_KEEPALIVE, (char *) &flag, sizeof(int)) != 0)
                        error("%llu: Cannot set SO_KEEPALIVE on socket.", w->id);
-
-
        }
 
        w->response.data = buffer_create(INITIAL_WEB_DATA_LENGTH);
@@ -446,6 +443,8 @@ int mysendfile(struct web_client *w, char *filename)
                        return 404;
                }
        }
+       if(fcntl(w->ifd, F_SETFL, O_NONBLOCK) < 0)
+               error("%llu: Cannot set O_NONBLOCK on file '%s'.", w->id, webfilename);
 
        // pick a Content-Type for the file
                 if(strstr(filename, ".html") != NULL)  w->response.data->contenttype = CT_TEXT_HTML;
@@ -1877,6 +1876,7 @@ void web_client_process(struct web_client *w) {
                                        else
                                                buffer_strcat(w->response.data, "I am doing it already");
 
+                                       error("web request to exit received.");
                                        netdata_exit = 1;
                                }
                                else if(hash == hash_debug && strcmp(tok, "debug") == 0) {
index f4e0f498dc34d42f70f7eda408de7731e16b2f81..9d5497431ef75c6f3446da6c1c50925eda090c0b 100644 (file)
@@ -51,6 +51,39 @@ static void log_allocations(void)
 }
 #endif
 
+#ifndef HAVE_ACCEPT4
+int accept4(int sock, struct sockaddr *addr, socklen_t *addrlen, int flags) {
+       int fd = accept(sock, addr, addrlen);
+       int newflags = 0;
+
+       if (fd < 0) return fd;
+
+       if (flags & SOCK_NONBLOCK) {
+               newflags |= O_NONBLOCK;
+               flags &= ~SOCK_NONBLOCK;
+       }
+
+       if (flags & SOCK_CLOEXEC) {
+               newflags |= O_CLOEXEC;
+               flags &= ~SOCK_CLOEXEC;
+       }
+
+       if (flags) {
+               errno = -EINVAL;
+               return -1;
+       }
+
+       if (fcntl(fd, F_SETFL, newflags) < 0) {
+               int saved_errno = errno;
+               close(fd);
+               errno = saved_errno;
+               return -1;
+       }
+
+       return fd;
+}
+#endif
+
 static int is_ip_anything(const char *ip)
 {
        if(!ip || !*ip
index 5df6bfa71c8456fbf67f254ce116c4f1a06b2a04..bd1001f90f4855c26c75b6574f91d0a15ec81f25 100644 (file)
@@ -23,4 +23,17 @@ extern void *socket_listen_main_multi_threaded(void *ptr);
 extern void *socket_listen_main_single_threaded(void *ptr);
 extern int create_listen_socket(void);
 
+#ifndef HAVE_ACCEPT4
+extern int accept4(int sock, struct sockaddr *addr, socklen_t *addrlen, int flags);
+
+#ifndef SOCK_NONBLOCK
+#define SOCK_NONBLOCK 00004000
+#endif  /* #ifndef SOCK_NONBLOCK */
+
+#ifndef SOCK_CLOEXEC
+#define SOCK_CLOEXEC 02000000
+#endif /* #ifndef SOCK_CLOEXEC */
+
+#endif /* #ifndef HAVE_ACCEPT4 */
+
 #endif /* NETDATA_WEB_SERVER_H */