Python PySide/Cython和GIL多线程使用

Python PySide/Cython和GIL多线程使用,python,multithreading,qt,pyside,cython,Python,Multithreading,Qt,Pyside,Cython,几天来,我一直在为一个PySide/Cython多线程应用程序苦苦挣扎。 将问题分成几个部分,我参加了一个使用valgrind/helgrind运行的测试(请参见下面的一个错误条目)。 C函数(下面的CHLoneload)使用Python及其GIL(不向Cython发出指令), Shiboken也可以访问GIL。 输出表明与GIL访问存在冲突(除非我错了),但我的 据了解,GIL的存在是为了避免这种冲突 Shiboken执行一些与另一个线程上的PyList\u New冲突的解除锁定 我迷路了,

几天来,我一直在为一个PySide/Cython多线程应用程序苦苦挣扎。
将问题分成几个部分,我参加了一个使用valgrind/helgrind运行的测试(请参见下面的一个错误条目)。
C函数(下面的CHLone
load
)使用Python及其GIL(不向Cython发出指令), Shiboken也可以访问GIL。
输出表明与GIL访问存在冲突(除非我错了),但我的 据了解,GIL的存在是为了避免这种冲突

Shiboken执行一些与另一个线程上的
PyList\u New
冲突的解除锁定

我迷路了,
我以为GIL负责阻止PyList_New,而另一个线程正在修改一些Python共享数据。或者是石破门忘记上锁了吗

listobject.c
第161行是对
\u PyObject\u GC\u TRACK()
的调用,该调用(我假设)要求GC跟踪新对象。
classobject.c
第2360行是对
\u PyObject\u GC\u UNTRACK()
的调用,看起来很像是要求GC停止跟踪对象…
我认为,helfrinddiag是一种可能的数据竞争,但事实上,这会导致核心转储,我不喜欢在使用线程时在pythongc上使用这个可能的词。我想先修一下这个

==26535== ----------------------------------------------------------------
==26535== 
==26535== Possible data race during read of size 8 at 0x4FE8488 by thread #2
==26535== Locks held: none
==26535==    at 0x4C92A80: PyList_New (listobject.c:161)
==26535==    by 0x742C43F: s2p_parseAndReadHDF (SIDStoPython.c:949)
==26535==    by 0x742C5C4: s2p_parseAndReadHDF (SIDStoPython.c:968)
==26535==    by 0x742E638: s2p_loadAsHDF (SIDStoPython.c:1485)
==26535==    by 0x741C3CC: __pyx_f_6CHLone_load (pyCHLone.c:2182)
==26535==    by 0x741D2AD: __pyx_pf_6CHLone_12load (pyCHLone.c:2422)
==26535==    by 0x741D1C3: __pyx_pw_6CHLone_13load (pyCHLone.c:2392)
==26535==    by 0x4D0A48F: PyEval_EvalFrameEx (ceval.c:4013)
==26535==    by 0x4D0C3DC: PyEval_EvalCodeEx (ceval.c:3253)
==26535==    by 0x4C8B641: function_call (funcobject.c:526)
==26535==    by 0x4C5F652: PyObject_Call (abstract.c:2529)
==26535==    by 0x4C7279E: instancemethod_call (classobject.c:2578)
==26535== 
==26535== This conflicts with a previous write of size 8 by thread #1
==26535== Locks held: none
==26535==    at 0x4C6C53F: instancemethod_dealloc (classobject.c:2360)
==26535==    by 0x5AB248A: Shiboken::AutoDecRef::~AutoDecRef() (in /tmp/tools-2/local/x86z/lib/python2.7/site-packages/PySide/QtCore.so)
==26535==    by 0x5F9736F: PySide::GlobalReceiverV2::qt_metacall(QMetaObject::Call, int, void**) (in /tmp/tools-2/local/x86z/lib/libpyside-python2.7.so.1.0.9)
==26535==    by 0x659BCA5: QObject::event(QEvent*) (in /tmp/tools-2/local/x86z/lib/libQtCore.so.4.8.0)
==26535==    by 0x5B038C5: QCoreApplicationWrapper::notify(QObject*, QEvent*) (in /tmp/tools-2/local/x86z/lib/python2.7/site-packages/PySide/QtCore.so)
==26535==    by 0x6586F8B: QCoreApplication::notifyInternal(QObject*, QEvent*) (in /tmp/tools-2/local/x86z/lib/libQtCore.so.4.8.0)
==26535==    by 0x658A5A7: QCoreApplicationPrivate::sendPostedEvents(QObject*, int, QThreadData*) (in /tmp/tools-2/local/x86z/lib/libQtCore.so.4.8.0)
==26535==    by 0x65B60F2: ??? (in /tmp/tools-2/local/x86z/lib/libQtCore.so.4.8.0)
==26535==
问题:
1.我认为GIL的行为正确吗?
2.如果
... 这是否意味着我必须自己管理每个线程中的GIL锁?
... 然后我必须为Python创建自己的互斥锁
3.如果
... 关于GIL的使用,我的Cython或C库中有问题吗?

... 这可能是QThread/QMutex的副作用吗

在CPython中,全局解释器锁(GIL)是一个互斥锁,用于防止多个本机线程同时执行Python字节码

因此,您可以从GIL中期望的是,它可以防止两个python代码流同时执行。除此之外,您不应该期望出现任何类型的锁定行为。编写依赖GIL保护您的代码通常是不好的做法。GIL是一个很多人都想消除的缺点,在某些python形式中,比如IronPython和jython,GIL并不存在。在它确实存在的地方,它减少了并发性,增加了开销,使python代码比其他情况下更难推理

从上面看,我不清楚是否涉及GIL故障。第二条轨迹似乎是在C++的地盘深处,而不是在我理解吉尔限制的区域。