我想从 python 创建 .so 文件并在 C 中执行 .so 文件。为此,我使用 cython 将 .pyx 转换为 .so
## print_me.pyx
cimport numpy as cnp
import numpy as np
cimport cython
cpdef public char* print_me(f):
# I know this numpy line does nothing
cdef cnp.ndarray[cnp.complex128_t, ndim=3] a = np.zeros((3,3,3), dtype=np.complex128)
return f
然后我使用 setup.py 将 .pyx 实际转换为 .so
## setup.py
from distutils.core import setup
from Cython.Build import cythonize
import numpy as np
setup(
ext_modules=cythonize("print_me.pyx"),
include_dirs=[np.get_include()]
)
通过运行以下命令行,我能够创建 .so 文件
python setup.py build_ext --inplace
当我尝试使用以下 C 代码运行 so 文件时,出现分段错误。
/* toloadso.c */
#include <stdio.h>
#include <stdlib.h>
#include <dlfcn.h>
#include <time.h>
#include <python2.7/Python.h>
int main(void)
{
// define function
void *handle;
char* (*print_me)(PyObject*);
char *error;
PyObject* filename = PyString_FromString("hello");
// load so file
handle = dlopen("./print_me.so", RTLD_LAZY);
if (!handle) {
fprintf(stderr, "%s\n", dlerror());
exit(EXIT_FAILURE);
}
dlerror();
// get function handler from so file
print_me = (char* (*)(PyObject*))dlsym(handle, "print_me");
// check if handler got error
error = dlerror();
if (error != NULL) {
fprintf(stderr, "%s\n", error);
exit(EXIT_FAILURE);
}
// execute loaded function
printf("%s\n", (char*)(*print_me)(filename));
dlclose(handle);
exit(EXIT_SUCCESS);
}
我使用以下命令编译了这个 .c 文件:
gcc -fPIC -I/usr/include/ -o toloadso toloadso.c -lpython2.7 -ldl
(It compiled without error or warning)
当我尝试运行此代码时,出现分段错误
[root@localhost ~]# ./toloadso
Segmentation fault
如果我在 print_me.pyx 中注释掉以下行
cdef cnp.ndarray[cnp.complex128_t, ndim=3] a = np.zeros((3,3,3), dtype=np.complex128)
我的 C 代码运行没有错误,但是一旦我取消注释这一行,它就不起作用。我认为尝试在 cython 中使用 numpy 会以某种方式产生错误。
我该怎么修??我非常感谢你的回复
您必须通过调用import_array()
来初始化 numpy C API。
将此行添加到您的 cython 文件中:
cnp.import_array()
正如在评论中指出@ user4815162342和@DavidW,你必须调用Py_Initialize()
和Py_Finalize()
中main()
。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句