[Pythonmac-SIG] Python threading.Thread vs PyObjC performOnMainThread

Bob Ippolito bob at redivi.com
Mon May 16 22:40:48 CEST 2005


On May 16, 2005, at 4:29 PM, gandreas at gandreas.com wrote:

> On May 16, 2005, at 2:39 PM, Ronald Oussoren wrote:
>
>
>> On 16-mei-2005, at 21:28, gandreas at gandreas.com wrote:
>>
>>
>>> The  problem isn't the Cocoa threads (Cocoa knows that the  
>>> application is multithreaded).  The problem is that the python  
>>> code that is executing in a threading.Thread calls  
>>> performSelectorOnMainThread to do the UI on the main thread  
>>> (which, since waits for that to complete, blocking the  
>>> interpreter).  The selector called in turn tries to interpret  
>>> additional Python code, but can't because the lock is held by the  
>>> blocked threading.Thread and a simple case of deadlock occurs.
>>
>> That should never occur. All calls into ObjC should give up the  
>> GIL. That is, during 'performSelectorOnMainThread' the GIL should  
>> be free for the taking, and the mail thread should be able to pick  
>> it up. If that doesn't work you ran into a bug in PyObjC (or  
>> python itself, we have had problems with GIL-related code in the  
>> past). You'd run into the same problem using NSThread.
>
> I'm more than willing to admit that there is some other problem  
> here with threading, GIL, etc... and that what I'm seeing is only  
> another symptom of that bigger problem, because I just discovered  
> that if I do the "debug using the local interpreter and absolutely  
> no extra threads ever generated for anything" I get:
>
> Fatal Python error: PyThreadState_Get: no current thread
>
> so it's probably something bad as a result of updating to Tiger (I  
> know there was a perfectly fine main thread which way up the call  
> chain responded to the menu command to start debugging, executed a  
> boatload of python code, and then loaded a NIB and in that  
> awakeFromNib a call to PyImport_AddModule sent it screaming down to  
> SIGABRT land):

You're probably not embedding Python correctly.  You should really be  
using a Python-based py2app generated plugin, as it saves you the  
trouble of figuring out how to do it correctly.

The procedure is documented in the embedding tutorial:
http://svn.red-bean.com/pyobjc/trunk/pyobjc/Doc/tutorial_embed/ 
extending_objc_with_python.html

Using this approach, you shouldn't have to write a SINGLE LINE of  
Python C API code anywhere in your application.  You simply define  
classes in your plugin and use -[NSBundle classNamed:] or  
NSClassFromString() to get references to them from the Objective-C  
shell.  PyObjC will take care of doing all the rest, and py2app's  
plugin bootstrap takes care of initializing Python properly.

The added bonus is that py2app will go through the trouble of  
embedding Python itself and the subset of the standard library (if  
not using the /System Python) as well as third party extensions you  
use (always)... so you automatically have a complete and rather  
isolated (depending on whether you use the system python or not)  
environment so that users won't break your app accidentally.

-bob



More information about the Pythonmac-SIG mailing list