From 0ff04d9b7764b9fcca58eed7cd8788f67fa143b9 Mon Sep 17 00:00:00 2001
From: Matthias Vogelgesang <matthias.vogelgesang@kit.edu>
Date: Thu, 23 Oct 2014 11:38:02 +0200
Subject: Add Python support code to release GIL on grab

A compile time switch WITH_PYTHON_MULTITHREADING has been added that toggles GIL
releasing.
---
 src/CMakeLists.txt | 14 ++++++++++++++
 src/config.h.in    |  1 +
 src/uca-camera.c   | 27 ++++++++++++++++++++++++++-
 3 files changed, 41 insertions(+), 1 deletion(-)

(limited to 'src')

diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index 3ae5422..3d94c98 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -46,6 +46,20 @@ set_target_properties(uca PROPERTIES
       SOVERSION ${UCA_ABI_VERSION})
 
 target_link_libraries(uca ${UCA_DEPS})
+#}}}
+#{{{ Python
+
+pkg_check_modules(PYTHON python)
+
+if (PYTHON_FOUND)
+    option(WITH_PYTHON_MULTITHREADING "Enable Python multithreading support" ON)
+
+    if (WITH_PYTHON_MULTITHREADING)
+        include_directories(${PYTHON_INCLUDE_DIRS})
+        target_link_libraries(uca ${PYTHON_LIBRARIES})
+    endif ()
+endif ()
+
 #}}}
 #{{{ GObject introspection
 if (INTROSPECTION_SCANNER AND INTROSPECTION_COMPILER)
diff --git a/src/config.h.in b/src/config.h.in
index a98cb00..8b11c60 100644
--- a/src/config.h.in
+++ b/src/config.h.in
@@ -1,3 +1,4 @@
+#cmakedefine WITH_PYTHON_MULTITHREADING     1
 #cmakedefine HAVE_PCO_CL
 #cmakedefine HAVE_PHOTON_FOCUS
 #cmakedefine HAVE_PHOTRON_FASTCAM
diff --git a/src/uca-camera.c b/src/uca-camera.c
index ef5f671..bd9c437 100644
--- a/src/uca-camera.c
+++ b/src/uca-camera.c
@@ -23,9 +23,14 @@
  * UcaCamera is the base camera from which a real hardware camera derives from.
  */
 
+#include "config.h"
+
+#ifdef WITH_PYTHON_MULTITHREADING
+#include <Python.h>
+#endif
+
 #include <glib.h>
 #include <string.h>
-#include "config.h"
 #include "compat.h"
 #include "uca-camera.h"
 #include "uca-ring-buffer.h"
@@ -579,6 +584,12 @@ uca_camera_init (UcaCamera *camera)
     uca_camera_set_property_unit (camera_properties[PROP_ROI_WIDTH_MULTIPLIER], UCA_UNIT_COUNT);
     uca_camera_set_property_unit (camera_properties[PROP_ROI_HEIGHT_MULTIPLIER], UCA_UNIT_COUNT);
     uca_camera_set_property_unit (camera_properties[PROP_RECORDED_FRAMES], UCA_UNIT_COUNT);
+
+#ifdef WITH_PYTHON_MULTITHREADING
+    if (!PyEval_ThreadsInitialized ()) {
+        PyEval_InitThreads ();
+    }
+#endif
 }
 
 static gpointer
@@ -937,7 +948,21 @@ uca_camera_grab (UcaCamera *camera, gpointer data, GError **error)
         }
         else {
             g_static_mutex_lock (&access_lock);
+
+#ifdef WITH_PYTHON_MULTITHREADING
+            if (Py_IsInitialized ()) {
+                PyGILState_STATE state = PyGILState_Ensure ();
+                Py_BEGIN_ALLOW_THREADS
+
+                result = (*klass->grab) (camera, data, error);
+
+                Py_END_ALLOW_THREADS
+                PyGILState_Release (state);
+            }
+#else
             result = (*klass->grab) (camera, data, error);
+#endif
+
             g_static_mutex_unlock (&access_lock);
         }
 
-- 
cgit v1.2.3