我是第一次用python写代码。想从python调用C共享库函数,但是问题是无法传递包含自定义数据类型的结构。
mylib.c
#include <stdio.h>
typedef int integer;
typedef char character;
struct temp {
integer a;
character b;
};
void
do_something(
struct temp *abc)
{
abc->a = 100;
abc->b = 'M';
return;
}
<<p>编译步骤/strong># gcc -fPIC -shared -o mylib.so mylib.c
请考虑整型和字符作为一些其他用户定义的数据类型,虽然在上面的例子中,它们是原始数据类型int和char的类型定义,但在我的情况下,它们不是,有2或3个级别的间接用于各种情况,如机器是32位或64位,或者如果在solaris, AIX或Linux等上工作。
我已经写了一个示例python程序也工作良好,如果我使用ctypes.c_int和ctypes.c_char,但我想使用integer性格和python代码中的自定义数据类型。基本上想写python代码,因为它不依赖于实际的基本类型。
Python3项目
import ctypes
class sample(ctypes.Structure):
_fields_ = [
("a", ctypes.c_int),
("b", ctypes.c_char)]
s = sample()
do_something = ctypes.CDLL("/root/Documents/python/mylib.so").do_something
do_something.argtypes = [ctypes.POINTER(sample)]
do_something(s)
print(s.a)
print(s.b)
输出:
100
b'M'
谢谢!
回复@Mark Tolonen查询
虽然我不能粘贴实际代码,但下面的代码与实际代码非常相似,这里的结构体具有pid_t字段(虽然它目前是内部整数类型,但我认为依赖于这个事实并不好),时间结构和文件大小可以根据OFFSET64声明进行更改。
我想要struct info(在python代码中分配)从C库中填充。
#include <unistd.h>
#include <sys/time.h>
typedef unsigned int __filesize;
typedef unsigned long long __filesize64;
typedef unsigned long inode_t;
#ifndef OFFSET64
typedef __filesize filesize;
#endif
#ifdef OFFSET64
typedef __filesize64 filesize;
#endif
struct info {
pid_t pid;
struct timeval atime;
filesize sz;
inode_t i_number;
};
void
did_something(
struct info *p_info)
{
p_info->pid = getpid();
gettimeofday(&p_info->atime, NULL);
p_info->sz = 512;
p_info->i_number = 2;
return;
}
我没有去挖掘pid_t
,timeval
或inode_t
的定义,但既然提供了filesize
的定义,这里有一种定义它的方法:
OFFSET64 = True # or False
if OFFSET64:
filesize = ctypes.c_ulonglong
else:
filesize = ctypes.c_uint
然后在结构的类定义中使用filesize
:
class info(ctypes.Structure):
_fields_ = (...
('sz', filesize),
...)
<代码>代码>