main: stop the scheduler in olsr_shutdown
authorFerry Huberts <ferry.huberts@pelagic.nl>
Wed, 11 Nov 2015 11:37:12 +0000 (12:37 +0100)
committerFerry Huberts <ferry.huberts@pelagic.nl>
Wed, 11 Nov 2015 16:09:28 +0000 (17:09 +0100)
Signed-off-by: Ferry Huberts <ferry.huberts@pelagic.nl>
src/defs.h
src/main.c
src/scheduler.c
src/scheduler.h

index 2c3cc76..80c1a4d 100644 (file)
@@ -187,11 +187,6 @@ extern struct olsrd_config *olsr_cnf;
 extern uint32_t now_times;              /* current idea of times(2) reported uptime */
 extern struct olsr_cookie_info *def_timer_ci;
 
 extern uint32_t now_times;              /* current idea of times(2) reported uptime */
 extern struct olsr_cookie_info *def_timer_ci;
 
-#if defined _WIN32
-extern bool olsr_win32_end_request;
-extern bool olsr_win32_end_flag;
-#endif /* defined _WIN32 */
-
 /*
  *IPC functions
  *These are moved to a plugin soon
 /*
  *IPC functions
  *These are moved to a plugin soon
index 7ced68a..2a456c7 100644 (file)
@@ -82,8 +82,6 @@
 int __stdcall SignalHandler(unsigned long signo) __attribute__ ((noreturn));
 void ListInterfaces(void);
 void DisableIcmpRedirects(void);
 int __stdcall SignalHandler(unsigned long signo) __attribute__ ((noreturn));
 void ListInterfaces(void);
 void DisableIcmpRedirects(void);
-bool olsr_win32_end_request = false;
-bool olsr_win32_end_flag = false;
 #else /* _WIN32 */
 static void olsr_shutdown(int) __attribute__ ((noreturn));
 #endif /* _WIN32 */
 #else /* _WIN32 */
 static void olsr_shutdown(int) __attribute__ ((noreturn));
 #endif /* _WIN32 */
@@ -450,8 +448,9 @@ int main(int argc, char *argv[]) {
   /* Starting scheduler */
   olsr_scheduler();
 
   /* Starting scheduler */
   olsr_scheduler();
 
-  /* Like we're ever going to reach this ;-) */
-  olsr_exit(NULL, 0);
+  /* We'll only get here when olsr_shutdown has stopped the scheduler */
+  sleep(30);
+  exit(1);
 } /* main */
 
 #ifndef _WIN32
 } /* main */
 
 #ifndef _WIN32
@@ -536,16 +535,8 @@ static void olsr_shutdown(int signo __attribute__ ((unused)))
 
   OLSR_PRINTF(1, "Received signal %d - shutting down\n", (int)signo);
 
 
   OLSR_PRINTF(1, "Received signal %d - shutting down\n", (int)signo);
 
-#ifdef _WIN32
-  OLSR_PRINTF(1, "Waiting for the scheduler to stop.\n");
-
-  olsr_win32_end_request = TRUE;
-
-  while (!olsr_win32_end_flag)
-  sleep(1);
-
-  OLSR_PRINTF(1, "Scheduler stopped.\n");
-#endif /* _WIN32 */
+  /* instruct the scheduler to stop */
+  olsr_scheduler_stop();
 
   /* clear all links and send empty hellos/tcs */
   olsr_reset_all_links();
 
   /* clear all links and send empty hellos/tcs */
   olsr_reset_all_links();
index dc979ce..6f7c4b7 100644 (file)
@@ -452,6 +452,24 @@ handle_fds(uint32_t next_interval)
   } OLSR_FOR_ALL_SOCKETS_END(entry);
 }
 
   } OLSR_FOR_ALL_SOCKETS_END(entry);
 }
 
+typedef enum {
+  INIT, RUNNING, STOPPING, ENDED
+} state_t;
+
+static volatile state_t state = INIT;
+
+static bool olsr_scheduler_is_stopped(void) {
+  return ((state == INIT) || (state == ENDED));
+}
+
+void olsr_scheduler_stop(void) {
+  if (olsr_scheduler_is_stopped()) {
+    return;
+  }
+
+  state = STOPPING;
+}
+
 /**
  * Main scheduler event loop. Polls at every
  * sched_poll_interval and calls all functions
 /**
  * Main scheduler event loop. Polls at every
  * sched_poll_interval and calls all functions
@@ -461,13 +479,13 @@ handle_fds(uint32_t next_interval)
  *
  * @return nada
  */
  *
  * @return nada
  */
-void __attribute__ ((noreturn))
-olsr_scheduler(void)
+void olsr_scheduler(void)
 {
 {
+  state = RUNNING;
   OLSR_PRINTF(1, "Scheduler started - polling every %d ms\n", (int)(olsr_cnf->pollrate*1000));
 
   /* Main scheduler loop */
   OLSR_PRINTF(1, "Scheduler started - polling every %d ms\n", (int)(olsr_cnf->pollrate*1000));
 
   /* Main scheduler loop */
-  while (true) {
+  while (state == RUNNING) {
     uint32_t next_interval;
 
     /*
     uint32_t next_interval;
 
     /*
@@ -480,12 +498,24 @@ olsr_scheduler(void)
     /* Read incoming data */
     poll_sockets();
 
     /* Read incoming data */
     poll_sockets();
 
+    if (state != RUNNING) {
+      break;
+    }
+
     /* Process timers */
     walk_timers(&timer_last_run);
 
     /* Process timers */
     walk_timers(&timer_last_run);
 
+    if (state != RUNNING) {
+      break;
+    }
+
     /* Update */
     olsr_process_changes();
 
     /* Update */
     olsr_process_changes();
 
+    if (state != RUNNING) {
+      break;
+    }
+
     /* Check for changes in topology */
     if (link_changes) {
       increase_local_ansn();
     /* Check for changes in topology */
     if (link_changes) {
       increase_local_ansn();
@@ -493,15 +523,15 @@ olsr_scheduler(void)
       link_changes = false;
     }
 
       link_changes = false;
     }
 
+    if (state != RUNNING) {
+      break;
+    }
+
     /* Read incoming data and handle it immediiately */
     handle_fds(next_interval);
     /* Read incoming data and handle it immediiately */
     handle_fds(next_interval);
-
-#ifdef _WIN32
-    if (olsr_win32_end_request) {
-      olsr_win32_end_flag = true;
-    }
-#endif /* _WIN32 */
   }
   }
+
+  state = ENDED;
 }
 
 /**
 }
 
 /**
index 8995978..a18198b 100644 (file)
@@ -105,6 +105,7 @@ const char *olsr_wallclock_string(void);
 
 /* Main scheduler loop */
 void olsr_scheduler(void);
 
 /* Main scheduler loop */
 void olsr_scheduler(void);
+void olsr_scheduler_stop(void);
 
 /*
  * Provides a timestamp s1 milliseconds in the future
 
 /*
  * Provides a timestamp s1 milliseconds in the future