Python 3.5.2
当我尝试使用ctypes调用C DLL时,我注意到这个问题,C函数类似于:
MEASURE_API int InitTester(char *ipAddress)
所以我需要将一个IP地址字符串(例如,192.168.100.100)从Python传递给ctypes,根据Python 3.5的ctypes doc,我尝试了c_wchar_p和c_char_p,但没有一个他们工作,我从c dll方面重新获得了错误代码。我有一些其他函数调用这个dll传递c_int,c_void_p,c_bool和其他数据类型都可以。追溯并发现c_wchar_p和c_char_p返回结果的行为与基于ctypes doc的结果不同。来自Python 3.5的ctypes doc:
>>> c_wchar_p("Hello, World")
c_wchar_p('Hello, World')
它返回ctypes字符串。 但是我在Python控制台中执行相同cmd的结果:
>>> from ctypes import *
>>> c_wchar_p("Hello, World")
c_wchar_p(1374004842736)
>>> c_wchar_p("Hello, World")
c_wchar_p(1374004841680)
>>> c_wchar_p("Hello, World")
c_wchar_p(1374004842736)
所以看起来orignial字符串部分可能成为内存地址。挖掘更多,并发现它是否是Python 2.x(默认编码是ASCII),然后返回显示像Python 3.5 ctypes doc所示的字符串。但是在Python 3.x(默认编码是UTF-8)中,它总是返回数字,行为与doc不同。检查多台PC。并且理解了我们可以使用.value返回原始字符串的部分。但它无法传递给必须是ctype的C函数。
提前多多感谢〜
答案 0 :(得分:0)
我现在更确定您应该使用create_string_buffer
代替c_char_p
将字符串传递给C
函数;非const
签名表示突变,并且需要文档中所述的字符缓冲区:
但是,你应该小心,不要将它们传递给期望指向可变内存的函数。如果你需要可变内存块,ctypes有一个
create_string_buffer()
函数可以创建各种内存块方法。可以使用raw属性访问(或更改)当前内存块内容;如果要以NUL
终止字符串的形式访问它,请使用value属性。
(强调我的)
所以实质上是create_string_buffer(b'192.168.100.100')
。
除此之外,似乎文档可能确实不在此处。 __repr__
for c_char_p
and c_wchar_p
的实现返回其名称,并且在创建了指向其内存缓冲区的指针后,.value
指向c_void_p
。