Hi Lennart, Praveen

If we don't have any comments, I would like to push the patch today

Thanks,
Minh

On 28/06/17 14:32, Minh Chau wrote:
In the scenario of shutting down SC while SC switchover is on going,
ntfd coredump is generated due to failure of pthread_mutex_destroy()
with errorcode:16(EBUSY). That means the mutex had been taken and
was not unlocked at the time phtread_mutex_destroy() is called.

This patch changes the way ntfd stops ntfimcn and cnsruvail_thread()
so that the cnsurvai_thread does not restart ntfimcn in stop sequence.
Therefore, when cnsurval_thread receives cancellation request, this
thread does not do anything that may lead to cancellation point with
a locked mutex.
---
  src/ntf/ntfd/ntfs_imcnutil.c | 58 +++++++++++++++++++++++++++++---------------
  1 file changed, 39 insertions(+), 19 deletions(-)

diff --git a/src/ntf/ntfd/ntfs_imcnutil.c b/src/ntf/ntfd/ntfs_imcnutil.c
index dd27a255c..cc257703b 100644
--- a/src/ntf/ntfd/ntfs_imcnutil.c
+++ b/src/ntf/ntfd/ntfs_imcnutil.c
@@ -44,6 +44,8 @@ typedef struct {
        SaAmfHAStateT ha_state;
        pid_t pid;
        pthread_t thread;
+       /* ntfimcn functionality: true(enabled), false(disabled)  */
+       bool ntfimcn_on;
  } init_params_t;
static init_params_t ipar;
@@ -240,8 +242,17 @@ static void *cnsurvail_thread(void *_init_params)
while (1) {
                osaf_mutex_lock_ordie(&ntfimcn_mutex);
-               pid = create_imcnprocess(ipar->ha_state);
-               ipar->pid = pid;
+               /* Only start ntfimcn process if this functionality is
+                * enabled, this is to avoid restarting ntfimcn when ntfd
+                * receives SIGTERM (shutting down)
+                * NOTE: Do not add any code outside below *if @ntfimcn_on*
+                * block that may lead to a thread cancellation point while
+                * ntfimcn_mutex is being locked
+                */
+               if (ipar->ntfimcn_on == true) {
+                       pid = create_imcnprocess(ipar->ha_state);
+                       ipar->pid = pid;
+               }
                osaf_mutex_unlock_ordie(&ntfimcn_mutex);
/* Wait for child process to exit */
@@ -271,7 +282,8 @@ static void *cnsurvail_thread(void *_init_params)
/**
   * Start the imcn process surveillance thread
- *
+ * When surveillance thread is running, this thread
+ * will start and monitor ntfimcn process in cnsurvail_thread()
   * @param ha_state[in]
   */
  static void start_cnprocess(SaAmfHAStateT ha_state)
@@ -285,7 +297,8 @@ static void start_cnprocess(SaAmfHAStateT ha_state)
                osaf_abort(rc);
ipar.ha_state = ha_state;
-
+       ipar.ntfimcn_on = true;
+       ipar.pid = 0;
        rc =
            pthread_create(&ipar.thread, NULL, cnsurvail_thread, (void *)&ipar);
        if (rc != 0)
@@ -330,33 +343,40 @@ void handle_state_ntfimcn(SaAmfHAStateT ha_state)
  }
/**
- * Cancel the surveillance trhead and kill the imcn process.
+ * This function stops functionality of ntfimcn by:
+ * First: Kill imcn process
+ * Second: Cancel the surveillance thread
+ * (in reversed order of start ntfimcn)
   * Use the pid and thread id saved when the process was started
   * This will terminate the process permanently.
   *
- * @return -1 if error
+ * @return 0 if success, abort() on any error
   */
  int stop_ntfimcn(void)
  {
-       void *join_ret;
        int rc = 0;
        TRACE_ENTER();
- if (ipar.ha_state != 0) {
-               TRACE("%s: Cancel the imcn surveillance thread", __FUNCTION__);
-               rc = pthread_cancel(ipar.thread);
-               if (rc != 0)
-                       osaf_abort(rc);
-               rc = pthread_join(ipar.thread, &join_ret);
-               if (rc != 0)
-                       osaf_abort(rc);
-               rc = pthread_mutex_destroy(&ntfimcn_mutex);
-               if (rc != 0)
-                       osaf_abort(rc);
-
+       /* Kill ntfimcn */
+       osaf_mutex_lock_ordie(&ntfimcn_mutex);
+       if (ipar.ntfimcn_on == true) {
+               ipar.ntfimcn_on = false;
                TRACE("%s: Terminating osafntfimcnd process", __FUNCTION__);
                timedwait_imcn_exit();
        }
+       osaf_mutex_unlock_ordie(&ntfimcn_mutex);
+
+       /* Cancel the surveillance thread */
+       TRACE("%s: Cancel the imcn surveillance thread", __FUNCTION__);
+       rc = pthread_cancel(ipar.thread);
+       if (rc != 0)
+               osaf_abort(rc);
+       rc = pthread_join(ipar.thread, NULL);
+       if (rc != 0)
+               osaf_abort(rc);
+       rc = pthread_mutex_destroy(&ntfimcn_mutex);
+       if (rc != 0)
+               osaf_abort(rc);
TRACE_LEAVE();
        return rc;


------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
_______________________________________________
Opensaf-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/opensaf-devel

Reply via email to