[Nodogsplash] [PATCH-0.9_beta9.9.6 1/4] Detach the thread automatically when finished

Sven Eckelmann sven at open-mesh.com
Fri Nov 8 18:58:05 CET 2013


The pthread_detach may be called when the thread is finished. Its resources
could already be free'd at this point but instead it is still waiting for a
pthread_join.

Setting the detaching behavior earlier (during the creation of the thread) is
the best method to avoid such a problem.

Signed-off-by: Sven Eckelmann <sven at open-mesh.com>
---
 src/gateway.c       | 14 ++++++++------
 src/ndsctl_thread.c |  5 +++--
 2 files changed, 11 insertions(+), 8 deletions(-)

diff --git a/src/gateway.c b/src/gateway.c
index c0d0352..6c1fe55 100644
--- a/src/gateway.c
+++ b/src/gateway.c
@@ -77,6 +77,7 @@ int created_httpd_threads;
 /* Number of current httpd request handling threads */
 int current_httpd_threads;
 
+pthread_attr_t thread_attr;
 
 /**@internal
  * @brief Handles SIGCHLD signals to avoid zombie processes
@@ -284,20 +285,18 @@ main_loop(void) {
   }
 
   /* Start client statistics and timeout clean-up thread */
-  result = pthread_create(&tid_client_check, NULL, (void *)thread_client_timeout_check, NULL);
+  result = pthread_create(&tid_client_check, &thread_attr, (void *)thread_client_timeout_check, NULL);
   if (result != 0) {
     debug(LOG_ERR, "FATAL: Failed to create thread_client_timeout_check - exiting");
     termination_handler(0);
   }
-  pthread_detach(tid_client_check);
 
   /* Start control thread */
-  result = pthread_create(&tid, NULL, (void *)thread_ndsctl, (void *)safe_strdup(config->ndsctl_sock));
+  result = pthread_create(&tid, &thread_attr, (void *)thread_ndsctl, (void *)safe_strdup(config->ndsctl_sock));
   if (result != 0) {
     debug(LOG_ERR, "FATAL: Failed to create thread_ndsctl - exiting");
     termination_handler(0);
   }
-  pthread_detach(tid);
 	
   /*
    * Enter the httpd request handling loop
@@ -349,12 +348,11 @@ main_loop(void) {
       *(params + 1) = r;
       *(params + 2) = thread_serial_num_p;
       created_httpd_threads++;
-      result = pthread_create(&tid, NULL, (void *)thread_httpd, (void *)params);
+      result = pthread_create(&tid, &thread_attr, (void *)thread_httpd, (void *)params);
       if (result != 0) {
 	debug(LOG_ERR, "FATAL: pthread_create failed to create httpd request thread - exiting...");
 	termination_handler(0);
       }
-      pthread_detach(tid);
     }
     else {
       /* webserver->lastError should be 2 */
@@ -388,6 +386,10 @@ int main(int argc, char **argv) {
   debug(LOG_NOTICE,"Initializing signal handlers");
   init_signals();
 
+  /* Init pthread behavior; detach automatically */
+  pthread_attr_init(&thread_attr);
+  pthread_attr_setdetachstate(&thread_attr, PTHREAD_CREATE_DETACHED);
+
   if (config->daemon) {
 
     debug(LOG_NOTICE, "Starting as daemon, forking to background");
diff --git a/src/ndsctl_thread.c b/src/ndsctl_thread.c
index 30b0a78..2ed192d 100644
--- a/src/ndsctl_thread.c
+++ b/src/ndsctl_thread.c
@@ -72,6 +72,8 @@ static void ndsctl_loglevel(int, char *);
 static void ndsctl_password(int, char *);
 static void ndsctl_username(int, char *);
 
+extern pthread_attr_t thread_attr;
+
 /** Launches a thread that monitors the control socket for request
 @param arg Must contain a pointer to a string containing the Unix domain socket to open
 @todo This thread loops infinitely, need a watchdog to verify that it is still running?
@@ -137,12 +139,11 @@ thread_ndsctl(void *arg) {
 	    strerror(errno));
     } else {
       debug(LOG_DEBUG, "Accepted connection on ndsctl socket %d (%s)", fd, sa_un.sun_path);
-      result = pthread_create(&tid, NULL, &thread_ndsctl_handler, (void *)fd);
+      result = pthread_create(&tid, &thread_attr, &thread_ndsctl_handler, (void *)fd);
       if (result != 0) {
 	debug(LOG_ERR, "FATAL: Failed to create a new thread (ndsctl handler) - exiting");
 	termination_handler(0);
       }
-      pthread_detach(tid);
     }
   }
 }
-- 
1.8.4.2




More information about the Nodogsplash mailing list