gpt4 book ai didi

python - C中多线程python扩展中的段错误

转载 作者:太空宇宙 更新时间:2023-11-03 11:11:19 28 4
gpt4 key购买 nike

我有一个非常精简的示例,它创建了一个我似乎无法摆脱的段错误。 Python 脚本调用扩展中的 C 函数,该函数使用 pthreads 创建一个新线程。我在新线程中围绕我的 python 调用 (PyRun_SimpleString) 使用 PyGILState_Ensure 和 PyGILState_Release,但也许我没有正确使用它们或者错过了其他一些步骤。注释掉 receive_audio 函数中的 python 调用,段错误不再发生。有什么想法吗?

输出:

python 库/test.py
(主线程) initmodule 完成
(主线程)调用 run_thread()
(主线程) 创建线程
(新线程)在 receive_audio() 中 - 获取 GIL
(新线程)python 打印!
(新线程)在 receive_audio() 中 - 发布了 GIL
(新线程) 循环 0
段错误

C代码如下:

PyMODINIT_FUNC streamaudio() {
PyObject *m = Py_InitModule("streamaudio", methods);
PyEval_InitThreads();
mainThreadState = PyThreadState_Get();
PyEval_ReleaseLock();
printf("(Main Thread) initmodule complete\n");
}

static PyObject* run_thread(PyObject* self, PyObject* args)
{
int ok, stream_id;
PyGILState_STATE gstate;
gstate = PyGILState_Ensure();
ok = PyArg_ParseTuple(args, "i", &stream_id);
PyRun_SimpleString("print '(Main Thread) Creating thread'\n");
int rc = pthread_create(&thread, NULL, receive_audio, (void*)stream_id);
PyRun_SimpleString("print '(Main Thread) Thread created'\n");
PyGILState_Release(gstate);
return Py_BuildValue("i", rc);
}

void* receive_audio(void *x)
{
printf("(New Thread) In receive_audio() - acquiring GIL\n");
PyGILState_STATE gstate;
gstate = PyGILState_Ensure();
PyRun_SimpleString("print '(New Thread) python print!'\n");
PyGILState_Release(gstate);
printf("(New Thread) In receive_audio() - released GIL\n");
int i;
for (i = 0; i < 100; i++) {
printf("(New Thread) Looping %d\n", i);
sleep(1);
}
}

最佳答案

我不确定这是否与您的问题相关,但看起来可疑的一件事是模块初始化函数中的 PyEval_ReleaseLock() 调用。我怀疑 Python 是否期望您的模块初始化程序从其下方释放 GIL,并快速查看一些示例代码 here在这些方面没有显示任何内容。您能否尝试删除 PyEval_ReleaseLock() 调用并告诉我们发生了什么?

顺便说一句,我同意 run_thread() 中的 PyGILState_*() 调用应该没有效果;你应该能够删除它们。

关于python - C中多线程python扩展中的段错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2478939/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com