1 #ifndef Py_INTERNAL_GIL_H 2 #define Py_INTERNAL_GIL_H 3 #ifdef __cplusplus 4 extern "C" { 5 #endif 6 7 #include "pyatomic.h" 8 9 #include "internal/condvar.h" 10 #ifndef Py_HAVE_CONDVAR 11 #error You need either a POSIX-compatible or a Windows system! 12 #endif 13 14 /* Enable if you want to force the switching of threads at least 15 every `interval`. */ 16 #undef FORCE_SWITCHING 17 #define FORCE_SWITCHING 18 19 struct _gil_runtime_state { 20 /* microseconds (the Python API uses seconds, though) */ 21 unsigned long interval; 22 /* Last PyThreadState holding / having held the GIL. This helps us 23 know whether anyone else was scheduled after we dropped the GIL. */ 24 _Py_atomic_address last_holder; 25 /* Whether the GIL is already taken (-1 if uninitialized). This is 26 atomic because it can be read without any lock taken in ceval.c. */ 27 _Py_atomic_int locked; 28 /* Number of GIL switches since the beginning. */ 29 unsigned long switch_number; 30 /* This condition variable allows one or several threads to wait 31 until the GIL is released. In addition, the mutex also protects 32 the above variables. */ 33 PyCOND_T cond; 34 PyMUTEX_T mutex; 35 #ifdef FORCE_SWITCHING 36 /* This condition variable helps the GIL-releasing thread wait for 37 a GIL-awaiting thread to be scheduled and take the GIL. */ 38 PyCOND_T switch_cond; 39 PyMUTEX_T switch_mutex; 40 #endif 41 }; 42 43 #ifdef __cplusplus 44 } 45 #endif 46 #endif /* !Py_INTERNAL_GIL_H */ 47