From f90995eec6ff44bb650379acb91c5373f0447d20 Mon Sep 17 00:00:00 2001
From: Tristan Walter <twalter@orn.mpg.de>
Date: Thu, 15 Oct 2020 14:25:33 +0200
Subject: [PATCH] preventing further dead-locks with pausing

---
 Application/src/tracker/gui/Timeline.cpp         |  2 +-
 Application/src/tracker/tracking/Posture.cpp     |  3 ++-
 Application/src/tracker/tracking/Recognition.cpp | 13 ++++---------
 Application/src/tracker/tracking/Tracker.cpp     | 13 +++++++++++--
 Application/src/tracker/tracking/Tracker.h       |  6 ++++++
 5 files changed, 24 insertions(+), 13 deletions(-)

diff --git a/Application/src/tracker/gui/Timeline.cpp b/Application/src/tracker/gui/Timeline.cpp
index fa7ebe1..2e57cd2 100644
--- a/Application/src/tracker/gui/Timeline.cpp
+++ b/Application/src/tracker/gui/Timeline.cpp
@@ -62,7 +62,7 @@ namespace gui {
         _status_text2.set_clickable(true);
         
         _pause.on_click([](auto) {
-            SETTING(analysis_paused) = !SETTING(analysis_paused);
+            Tracker::analysis_state((Tracker::AnalysisState)!SETTING(analysis_paused));
         });
         
         _update_events_thread = std::make_shared<std::thread>([this](){
diff --git a/Application/src/tracker/tracking/Posture.cpp b/Application/src/tracker/tracking/Posture.cpp
index 75e0b3b..dbb6386 100644
--- a/Application/src/tracker/tracking/Posture.cpp
+++ b/Application/src/tracker/tracking/Posture.cpp
@@ -412,7 +412,8 @@ namespace track {
                 
                 cv::cvtColor(colored, colored, cv::COLOR_BGR2RGB);
                 tf::imshow("image", colored);
-                SETTING(analysis_paused) = true;
+                
+                Tracker::analysis_state(Tracker::AnalysisState::PAUSED);
             }
         }
     }
diff --git a/Application/src/tracker/tracking/Recognition.cpp b/Application/src/tracker/tracking/Recognition.cpp
index cba8346..f998429 100644
--- a/Application/src/tracker/tracking/Recognition.cpp
+++ b/Application/src/tracker/tracking/Recognition.cpp
@@ -107,7 +107,7 @@ std::unique_ptr<Image> Recognition::calculate_diff_image_with_settings(const def
             Timer timer;
             std::mutex thread_mutex;
             std::unique_lock<std::mutex> guard(thread_mutex);
-            while (!SETTING(terminate) && !terminate_thread) {
+            while (!GUI_SETTINGS(terminate) && !terminate_thread) {
                 
                 bool wait_long(true);
                 auto info = _detail.info();
@@ -119,9 +119,7 @@ std::unique_ptr<Image> Recognition::calculate_diff_image_with_settings(const def
                 if(!FAST_SETTINGS(recognition_enable) || this->_running || timer.elapsed() < 1)
                     continue;
                 
-                //Debug("Calling update_internal_training...");
-                std::unique_lock<std::mutex> gil(_termination_mutex);
-                if(!SETTING(terminate) && !terminate_thread) {
+                if(!GUI_SETTINGS(terminate) && !terminate_thread) {
                     this->update_internal_training();
                 }
                 
@@ -229,7 +227,7 @@ std::unique_ptr<Image> Recognition::calculate_diff_image_with_settings(const def
     Recognition::~Recognition() {
         prepare_shutdown();
         
-        std::lock_guard<std::mutex> guard(_termination_mutex);
+        Tracker::LockGuard guard("update_dataset_quality");
         if(_dataset_quality)
             delete _dataset_quality;
     }
@@ -302,9 +300,7 @@ std::unique_ptr<Image> Recognition::calculate_diff_image_with_settings(const def
     }
     
     void Recognition::prepare_shutdown() {
-        std::unique_lock<std::mutex> gil(_termination_mutex);
         terminate_thread = true;
-        gil.unlock();
         
         if(update_thread) {
             update_thread->join();
@@ -1328,14 +1324,13 @@ std::unique_ptr<Image> Recognition::calculate_diff_image_with_settings(const def
                     }
                 }
                 
-                std::lock_guard<std::mutex> guard(_termination_mutex);
                 if(GUI::instance()) {
                     std::lock_guard<std::recursive_mutex> guard(GUI::instance()->gui().lock());
                     GUI::instance()->cache().set_tracking_dirty();
                     GUI::instance()->set_redraw();
                 }
 
-                if(SETTING(terminate))
+                if(GUI_SETTINGS(terminate))
                    break;
             }
            
diff --git a/Application/src/tracker/tracking/Tracker.cpp b/Application/src/tracker/tracking/Tracker.cpp
index eb50678..0c8c035 100644
--- a/Application/src/tracker/tracking/Tracker.cpp
+++ b/Application/src/tracker/tracking/Tracker.cpp
@@ -234,6 +234,14 @@ const FrameProperties* Tracker::properties(long_t frameIndex, const CacheHints*
         return _instance->_recognition;
     }
 
+void Tracker::analysis_state(AnalysisState pause) {
+    if(!instance())
+        U_EXCEPTION("No tracker instance can be used to pause.");
+    instance()->recognition_pool.enqueue([](bool value){
+        SETTING(analysis_paused) = value;
+    }, pause == AnalysisState::PAUSED);
+}
+
     Tracker::Tracker()
           : _thread_pool(max(1u, cmn::hardware_concurrency())),
             recognition_pool(max(1u, cmn::hardware_concurrency())),
@@ -484,7 +492,7 @@ const FrameProperties* Tracker::properties(long_t frameIndex, const CacheHints*
                 //bool analysis_paused = SETTING(analysis_paused);
                 GUI::reanalyse_from(first_change, true);
                 //if(!analysis_paused)
-                SETTING(analysis_paused) = false;
+                Tracker::analysis_state(Tracker::AnalysisState::UNPAUSED);
                 
                 /*add_work_queue("removing frames", [this, first_change](){
                     bool before = analysis()->is_paused();
@@ -4077,7 +4085,8 @@ void Tracker::update_iterator_maps(long_t frame, const Tracker::set_of_individua
                     SETTING(manual_matches) = automatic_matches;
                 if(after_frame == -1)
                     SETTING(manual_splits) = manual_splits;
-                SETTING(analysis_paused) = false;
+                
+                Tracker::analysis_state(Tracker::AnalysisState::UNPAUSED);
             }, "");
         }
         
diff --git a/Application/src/tracker/tracking/Tracker.h b/Application/src/tracker/tracking/Tracker.h
index b1447f6..0e160cb 100644
--- a/Application/src/tracker/tracking/Tracker.h
+++ b/Application/src/tracker/tracking/Tracker.h
@@ -284,6 +284,12 @@ CREATE_STRUCT(Settings,
         static void emergency_finish();
         static void delete_automatic_assignments(long_t fish_id, const FrameRange& frame_range);
         
+        enum class AnalysisState {
+            PAUSED,
+            UNPAUSED
+        };
+        static void analysis_state(AnalysisState);
+        
     protected:
         friend class track::Posture;
         static void increase_midline_errors() {
-- 
GitLab