我发现Swig未能生成typemap中定义的一些临时变量。
问题是:
我定义了一个类型映射如下。
%define %bound_buffer_input(TYPEMAP, SIZE)
%typemap(in) (TYPEMAP, SIZE)
(int res, Py_ssize_t size = 0, const void *buf = 0) {
res = PyObject_AsReadBuffer($input, &buf, &size);
if (res<0) {
PyErr_Clear();
%argument_fail(res, "(TYPEMAP, SIZE)", $symname, $argnum);
}
$1 = ($1_ltype) buf;
$2 = ($2_ltype) size;
}
%enddef
应用于2种情况:
%bound_buffer_input(const uint8_t* key, size_t keyLength);
%bound_buffer_input(void* buf, size_t length);
首先,它运行良好并生成正确的代码但对于第二个,它无法为函数生成正确的变量名:
void*MF_WriteOne(void*qry,int数据类型,void*buf,大小长度);
代码swig生成:
{
res3 = PyObject_AsReadBuffer(obj2, &buf3, &size3);
if (res3<0) {
PyErr_Clear();
SWIG_exception_fail(SWIG_ArgError(res3), "in method '" "MF_WriteOne" "', argument " "3"" of type '" "(void* buf, size_t length)""'");
}
arg3 = (void *) buf;
arg4 = (size_t) size3;
}
在第一行中,用名称“buf3”正确生成变量“buf”,但在第六行中,变量的名称“buf”不正确,而不是“buf3”。
稍后我将名称从“buf改为buff”,发现变量的名称都是正确的。
为什么会发生这么奇怪的事?
最佳答案
问题是您的类型映射有名称冲突传递给函数的变量名为buf
,变量名(预自动重命名)也为buf
。
SWIG试图变得聪明并使用上下文正确的方法,但这并不是你希望的行为可以通过以下几种方法之一解决此问题:
如您所述,重命名两个buf
s中的一个或两个
更改给定给宏的名称,但使用%apply
仍然匹配buf
作为参数名:
%module test
%define %bound_buffer_input(TYPEMAP, SIZE)
%typemap(in) (TYPEMAP, SIZE)
(int res, Py_ssize_t size = 0, const void *buf = 0) {
res = PyObject_AsReadBuffer($input, &buf, &size);
if (res<0) {
PyErr_Clear();
%argument_fail(res, "(TYPEMAP, SIZE)", $symname, $argnum);
}
$1 = ($1_ltype) buf;
$2 = ($2_ltype) size;
}
%enddef
%bound_buffer_input(const uint8_t* key, size_t keyLength);
%bound_buffer_input(void* buffer, size_t length);
%apply (void* buffer, size_t length) { (void* buf, size_t length) };
%inline %{
void test1(const uint8_t* key, size_t keyLength) {}
void test2(void* buf, size_t length) {}
%}
手动地自动重命名局部变量,在类型映射中使用
noblock=1
,不使用临时变量:%module test
%define %bound_buffer_input(TYPEMAP, SIZE)
%typemap(in,noblock=1) (TYPEMAP, SIZE) {
int res$argnum;
Py_ssize_t size$argnum = 0;
const void *buf$argnum = 0;
res$argnum = PyObject_AsReadBuffer($input, &buf$argnum, &size$argnum);
if (res$argnum<0) {
PyErr_Clear();
%argument_fail(res$argnum, "(TYPEMAP, SIZE)", $symname, $argnum);
}
$1 = ($1_ltype) buf$argnum;
$2 = ($2_ltype) size$argnum;
}
%enddef
%bound_buffer_input(const uint8_t* key, size_t keyLength);
%bound_buffer_input(void* buf, size_t length);
%inline %{
void test1(const uint8_t* key, size_t keyLength) {}
void test2(void* buf, size_t length) {}
%}
最后,除非您的目标是Python2.6及更高版本,否则应该use Python's newer memory views
关于python - Swig类型图中的临时变量生成,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/24613924/