mirror of
https://github.com/panda3d/panda3d.git
synced 2025-10-04 10:54:24 -04:00
change order of thread cleanup to avoid python crash
This commit is contained in:
parent
203c39ab7a
commit
3e4e3248e7
@ -45,7 +45,8 @@ init_thread_context(struct ThreadContext *context,
|
|||||||
makecontext(&context->_ucontext, (void (*)())&begin_context, 2, thread_func, data);
|
makecontext(&context->_ucontext, (void (*)())&begin_context, 2, thread_func, data);
|
||||||
}
|
}
|
||||||
|
|
||||||
void save_thread_context(struct ThreadContext *context,
|
void
|
||||||
|
save_thread_context(struct ThreadContext *context,
|
||||||
ContextFunction *next_context, void *data) {
|
ContextFunction *next_context, void *data) {
|
||||||
/* getcontext requires us to use a volatile auto variable to
|
/* getcontext requires us to use a volatile auto variable to
|
||||||
differentiate between pass 1 (immediate return) and pass 2
|
differentiate between pass 1 (immediate return) and pass 2
|
||||||
@ -297,7 +298,8 @@ init_thread_context(struct ThreadContext *context,
|
|||||||
setup_context_1();
|
setup_context_1();
|
||||||
}
|
}
|
||||||
|
|
||||||
void save_thread_context(struct ThreadContext *context,
|
void
|
||||||
|
save_thread_context(struct ThreadContext *context,
|
||||||
ContextFunction *next_context, void *data) {
|
ContextFunction *next_context, void *data) {
|
||||||
if (cs_setjmp(context->_jmp_context) != 0) {
|
if (cs_setjmp(context->_jmp_context) != 0) {
|
||||||
/* We have just returned from longjmp. In this case, return from
|
/* We have just returned from longjmp. In this case, return from
|
||||||
|
@ -33,13 +33,14 @@ PythonThread(PyObject *function, PyObject *args,
|
|||||||
const string &name, const string &sync_name) :
|
const string &name, const string &sync_name) :
|
||||||
Thread(name, sync_name)
|
Thread(name, sync_name)
|
||||||
{
|
{
|
||||||
|
_function = function;
|
||||||
|
Py_INCREF(_function);
|
||||||
|
_args = NULL;
|
||||||
_result = NULL;
|
_result = NULL;
|
||||||
|
|
||||||
_function = function;
|
|
||||||
if (!PyCallable_Check(_function)) {
|
if (!PyCallable_Check(_function)) {
|
||||||
nassert_raise("Invalid function passed to PythonThread constructor");
|
nassert_raise("Invalid function passed to PythonThread constructor");
|
||||||
}
|
}
|
||||||
Py_INCREF(_function);
|
|
||||||
|
|
||||||
if (args == Py_None) {
|
if (args == Py_None) {
|
||||||
// None means no arguments; create an empty tuple.
|
// None means no arguments; create an empty tuple.
|
||||||
@ -113,7 +114,7 @@ thread_main() {
|
|||||||
// thread state per OS-level thread, which is not true in the case
|
// thread state per OS-level thread, which is not true in the case
|
||||||
// of SIMPLE_THREADS.
|
// of SIMPLE_THREADS.
|
||||||
|
|
||||||
PyThreadState *orig_thread_state = PyThreadState_Swap(NULL);
|
PyThreadState *orig_thread_state = PyThreadState_Get();
|
||||||
PyInterpreterState *istate = orig_thread_state->interp;
|
PyInterpreterState *istate = orig_thread_state->interp;
|
||||||
PyThreadState *new_thread_state = PyThreadState_New(istate);
|
PyThreadState *new_thread_state = PyThreadState_New(istate);
|
||||||
PyThreadState_Swap(new_thread_state);
|
PyThreadState_Swap(new_thread_state);
|
||||||
|
@ -200,6 +200,14 @@ preempt(ThreadSimpleImpl *thread) {
|
|||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
void ThreadSimpleManager::
|
void ThreadSimpleManager::
|
||||||
next_context() {
|
next_context() {
|
||||||
|
// Delete any threads that need it. We can't delete the current
|
||||||
|
// thread, though.
|
||||||
|
while (!_finished.empty() && _finished.front() != _current_thread) {
|
||||||
|
ThreadSimpleImpl *finished_thread = _finished.front();
|
||||||
|
_finished.pop_front();
|
||||||
|
unref_delete(finished_thread->_parent_obj);
|
||||||
|
}
|
||||||
|
|
||||||
// Mark the current thread's resume point.
|
// Mark the current thread's resume point.
|
||||||
|
|
||||||
#ifdef HAVE_PYTHON
|
#ifdef HAVE_PYTHON
|
||||||
@ -268,6 +276,7 @@ prepare_for_exit() {
|
|||||||
|
|
||||||
next_context();
|
next_context();
|
||||||
|
|
||||||
|
// Delete any remaining threads.
|
||||||
while (!_finished.empty() && _finished.front() != _current_thread) {
|
while (!_finished.empty() && _finished.front() != _current_thread) {
|
||||||
ThreadSimpleImpl *finished_thread = _finished.front();
|
ThreadSimpleImpl *finished_thread = _finished.front();
|
||||||
_finished.pop_front();
|
_finished.pop_front();
|
||||||
@ -410,12 +419,6 @@ st_choose_next_context(void *data) {
|
|||||||
////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////
|
||||||
void ThreadSimpleManager::
|
void ThreadSimpleManager::
|
||||||
choose_next_context() {
|
choose_next_context() {
|
||||||
while (!_finished.empty() && _finished.front() != _current_thread) {
|
|
||||||
ThreadSimpleImpl *finished_thread = _finished.front();
|
|
||||||
_finished.pop_front();
|
|
||||||
unref_delete(finished_thread->_parent_obj);
|
|
||||||
}
|
|
||||||
|
|
||||||
_current_thread = NULL;
|
_current_thread = NULL;
|
||||||
|
|
||||||
double now = get_current_time();
|
double now = get_current_time();
|
||||||
|
Loading…
x
Reference in New Issue
Block a user