From 9ce9b0b466dde804a07148bac92cb8856f066684 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?C=C3=A9dric=20Traizet?= <cedric.traizet@c-s.fr>
Date: Tue, 8 Sep 2020 10:55:06 +0200
Subject: [PATCH] BUG: reacquire the GIL before calling callbacks in PyCommand

---
 .../Wrappers/SWIG/src/python/itkPyCommand.cxx | 24 +++++++++++++++++++
 1 file changed, 24 insertions(+)

diff --git a/Modules/Wrappers/SWIG/src/python/itkPyCommand.cxx b/Modules/Wrappers/SWIG/src/python/itkPyCommand.cxx
index 9f6acb0104..23c417949d 100644
--- a/Modules/Wrappers/SWIG/src/python/itkPyCommand.cxx
+++ b/Modules/Wrappers/SWIG/src/python/itkPyCommand.cxx
@@ -21,6 +21,27 @@
 
 #include "itkPyCommand.h"
 
+namespace
+{
+// Wrapper to automatics obtain and release GIL
+// RAII idiom
+class PyGILStateEnsure
+{
+public:
+  PyGILStateEnsure()
+    {
+      m_GIL = PyGILState_Ensure();
+    }
+  ~PyGILStateEnsure()
+    {
+      PyGILState_Release(m_GIL);
+    }
+private:
+  PyGILState_STATE m_GIL;
+};
+} // end anonymous namespace
+
+
 namespace itk
 {
 
@@ -33,6 +54,7 @@ PyCommand::~PyCommand()
 {
   if (this->obj)
   {
+    PyGILStateEnsure gil;
     Py_DECREF(this->obj);
   }
   this->obj = nullptr;
@@ -42,6 +64,7 @@ void PyCommand::SetCommandCallable(PyObject* theObj)
 {
   if (theObj != this->obj)
   {
+    PyGILStateEnsure gil;
     if (this->obj)
     {
       // get rid of our reference
@@ -89,6 +112,7 @@ void PyCommand::PyExecute()
   }
   else
   {
+    PyGILStateEnsure gil;
     PyObject* result;
 
     result = PyEval_CallObject(this->obj, (PyObject*)nullptr);
-- 
GitLab