From: Ovidiu Mircescu Date: Fri, 15 Oct 2021 12:18:38 +0000 (+0200) Subject: Workloadmanager deadlock on big foreach. X-Git-Tag: V9_8_0b1^0 X-Git-Url: http://git.salome-platform.org/gitweb/?a=commitdiff_plain;h=50712273d0129ca0c5e0fa79d831827ca1616092;p=modules%2Fyacs.git Workloadmanager deadlock on big foreach. --- diff --git a/src/workloadmanager/WorkloadManager.cxx b/src/workloadmanager/WorkloadManager.cxx index 98224019f..a364146bb 100644 --- a/src/workloadmanager/WorkloadManager.cxx +++ b/src/workloadmanager/WorkloadManager.cxx @@ -18,6 +18,9 @@ // #include "WorkloadManager.hxx" #include "Task.hxx" +#include +#include + namespace WorkloadManager { @@ -96,17 +99,21 @@ namespace WorkloadManager bool threadStop = false; while(!threadStop) { - std::unique_lock lock(_data_mutex); - _startCondition.wait(lock, [this] {return !_algo.empty() || _stop;}); - RunningInfo taskInfo; - while(chooseTaskToRun(taskInfo)) { - _runningTasks.emplace(taskInfo.id, std::async(std::launch::async, [this, taskInfo] - { - runOneTask(taskInfo); - })); + std::unique_lock lock(_data_mutex); + _startCondition.wait(lock, [this] {return !_algo.empty() || _stop;}); + RunningInfo taskInfo; + while(chooseTaskToRun(taskInfo)) + { + _runningTasks.emplace(taskInfo.id, std::async(std::launch::async, [this, taskInfo] + { + runOneTask(taskInfo); + })); + } + threadStop = _stop && _algo.empty(); } - threadStop = _stop && _algo.empty(); + // workaroud to release the lock and give a chance to other tasks to finish + std::this_thread::sleep_for(std::chrono::milliseconds(1)); } } diff --git a/src/yacsloader/samples/wlm_complex_foreach.xml b/src/yacsloader/samples/wlm_complex_foreach.xml new file mode 100644 index 000000000..7da065d85 --- /dev/null +++ b/src/yacsloader/samples/wlm_complex_foreach.xml @@ -0,0 +1,119 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + line02 testwait_for_me + testwait_for_me return_internal@PHY2S@Node + + line02 t + testwait_for_me timetowait + + + testwait_for_me a + return_internal@PHY2S@Node i0 + + + + + + + + test/one_state_calc return_internal@PHY2S@Node + + test/one_state_calc.return_internal@PHY2S@Node res + return_internal@PHY2S@Node i0 + + + + + UneForEach evalSamples + UneForEach.forEachBloc.test/one_state_calc.testget_search_state_option conditions + + + testgenerate_conditions UnBloc + + testgenerate_conditions conditions_list + UnBloc.UneForEach SmplsCollection + + + + test/run.UnBloc.UneForEach.forEachBloc.test/one_state_calc.testget_search_state_optionconditions + + + + test/run.UnBloc.UneForEach.forEachBloc.test/one_state_calc.testwait_for_metimetowait + + + diff --git a/src/yacsloader_swig/Test/testWorkloadManager.py b/src/yacsloader_swig/Test/testWorkloadManager.py index d1d610d43..ce20db9cb 100755 --- a/src/yacsloader_swig/Test/testWorkloadManager.py +++ b/src/yacsloader_swig/Test/testWorkloadManager.py @@ -119,6 +119,13 @@ class TestEdit(unittest.TestCase): self.assertEqual(proc.getState(),pilot.FAILED) self.assertEqual(proc.getChildByName("ErrorNode").getState(),pilot.ERROR) + def test5(self): + """ Foreach with 1000 points and several nodes in the block. + """ + proc = self.l.load("samples/wlm_complex_foreach.xml") + self.e.RunW(proc,0) + self.assertEqual(proc.getState(),pilot.DONE) + if __name__ == '__main__': dir_test = tempfile.mkdtemp(suffix=".yacstest") file_test = os.path.join(dir_test,"UnitTestsResult")