ten jest kontynuacją Call Python from C++Wywołanie Py_Finalize() z C
Przy uruchamianiu programm nazywam następującą funkcję aby zainicjować tłumacza:
void initPython(){
PyEval_InitThreads();
Py_Initialize();
PyEval_ReleaseLock();
}
Każdy wątek tworzy własną strukturę danych i nabywa zamek z:
PyGILState_STATE gstate;
gstate = PyGILState_Ensure();
//call python API, process results
PyGILState_Release(gstate);
raczej proste gdy zrozumiał Gil, ale problemem jest to, że mogę dostać się wysypać podczas wywoływania Py_Finalize().
void exitPython(){
PyEval_AcquireLock();
Py_Finalize();
}
Wniosek jest raczej wątpliwy o Py_Finalize() (a może jestem po prostu czytać wspak) i nie jestem pewien, czy PyEval_AcquireLock() można nabyć blokadę jeśli istnieje kilka aktywnych wątków i co się dzieje, jeśli istnieją aktywne wątki, gdy wywoływana jest funkcja Py_Finalize().
Anyways, otrzymuję segfault nawet jeśli jestem pewien, że wszystkie wątki zakończeniu swojej pracy, ale tylko wtedy, gdy co najmniej jedna została utworzona. Na przykład. Wywołanie initPython(), a następnie exitPython() nie powoduje żadnego błędu.
może po prostu zignorować problem i nadzieję, że OS wie, co robi, ale ja preferuję czy mogę dowiedzieć się, co się dzieje ..
Skomentowałem wszystko, ale PyGILState_Ensure() i Release() i błąd nadal występuje. Jeśli je również skomentuję, nie ma problemu .. – Voo
W tym przypadku, zgaduję, że jest coś w zarządzaniu wątkami, które nie jest wykonywane prawidłowo. Niestety odpowiednia strona C API ze wszystkimi funkcjami wątków nie jest oczywista, do których z tych połączeń potrzebujesz. – Kylotan
"Połączenia, których potrzebujesz" przez większość czasu to 'Py_BEGIN_ALLOW_THREADS' i jego odpowiednik. Są to z kolei makra, które używają 'PyEval_SaveThread()' i jej odpowiednika. Więc gdybym pisał coś w rodzaju OP, podążałbym za tym przykładem. – Kevin