Need some help with Python/C api and threading

Les Smithson lsmithso at NOhare.SPAM.demon.co.uk
Thu Jun 17 05:56:30 EDT 2004


>>>>> "Steve" == Steve Menard <steve.menard at videotron.ca> writes:

    Steve> Here is my problem.  I have this library thats hosts
    Steve> another language within python, and allows that language to
    Steve> call back INTO python.

    Steve> All is good as long as the other languages calls back on
    Steve> the same thread. If the callback arrives on a different
    Steve> thread, all hell break loose and the program dies horribly.

    Steve> looking at the C api documentation, I came upon the
    Steve> following block of code :

    Steve>      PyThreadState *tstate; PyObject *result;

    Steve>      /* interp is your reference to an interpreter
    Steve> object. */ tstate = PyThreadState_New(interp);
    Steve> PyEval_AcquireThread(tstate);

    Steve>      /* Perform Python actions here.  */ result =
    Steve> CallSomeFunction(); /* evaluate result */

    Steve>      /* Release the thread. No Python API allowed beyond
    Steve> this point. */ PyEval_ReleaseThread(tstate);

    Steve>      /* You can either delete the thread state, or save it
    Steve> until you need it the next time. */
    Steve> PyThreadState_Delete(tstate);


    Steve> Which would seem to be what I need. However, I have no idea
    Steve> how to get at that interp pointer. I tried the following :

    Steve> 		PyInterpreterState* interp =
    Steve> PyInterpreterState_New(); PyThreadState *tstate =
    Steve> PyThreadState_New(interp); PyEval_AcquireThread(tstate);

    Steve> but then it crashes on the second line ...

    Steve> Anybody ever done this? As a side note, the hosted language
    Steve> can start an arbitrary number of threads ...

    Steve> Steve

I haven't done this for a while and I'm a little hazy on it, so this
may be incorrect:

I used 'PyThreadState *ts = Py_NewInterpreter();' to set a new
sub-interpreter state if called in a new thread.

If the embedded script calls back into the extension, it restores that
thread state and acquires the GIL before making any other Py* calls by
calling 'PyEval_RestoreThread(ts);'. Before returning, it calls
'PyEval_SaveThread()'.





More information about the Python-list mailing list