假设我们正在用C编写一个CPython扩展模块。
定义扩展名时,我们需要提供PyMODINIT_FUNC PyInit_<module_name>(void)
。在此声明中没有指定本地调用约定。
无论是在Linux上还是在Windows上,扩展开发人员如何才能确保PyInit_
使用正确的调用约定来编译该函数,以便解释器在运行时成功调用该函数?Python标头中是否有一些魔术可以帮助我们解决此问题?或者是其他东西?
相同的问题适用于扩展模块中包含的本机函数,并暴露给包装为函数对象的Python。我们如何确保以与Python解释器调用约定兼容的方式进行编译?
你是在写作PyMODINIT_FUNC PyInit_<module_name>(void)
。现在PyMODINIT_FUNC
是一个宏,它扩展为由#ifdef
in中的各种s控制的不同事物pyport.h
。在当前的HEAD版本中,Github版本Python 3.9开发版本具有以下6个定义:
#define PyMODINIT_FUNC Py_EXPORTED_SYMBOL PyObject*
#define PyMODINIT_FUNC PyObject*
#define PyMODINIT_FUNC extern "C" Py_EXPORTED_SYMBOL PyObject*
#define PyMODINIT_FUNC Py_EXPORTED_SYMBOL PyObject*
#define PyMODINIT_FUNC extern "C" Py_EXPORTED_SYMBOL PyObject*
#define PyMODINIT_FUNC Py_EXPORTED_SYMBOL PyObject*
即,它可以扩展PyObject *
为返回类型,但也extern "C"
可以使用C ++编译器进行编译以确保针对该符号进行C链接,并且Py_EXPORTED_SYMBOL
在某些平台上也包含。
Py_EXPORTED_SYMBOL
被定义exports.h
为
#define Py_EXPORTED_SYMBOL __declspec(dllexport)
#define Py_EXPORTED_SYMBOL __attribute__ ((visibility ("default")))
#define Py_EXPORTED_SYMBOL
这些都没有指定调用约定,而是让函数默认使用cdecl约定...-还应注意,调用约定大部分仅在Windows中才有用。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句