`
xiaguangme
  • 浏览: 74225 次
  • 性别: Icon_minigender_1
  • 来自: 南京
社区版块
存档分类
最新评论

【转】当用 Python ctypes 模块调用动态链接库,如何传入一个结构体指针

阅读更多

转自http://www.dup2.org/node/150

当用 Python ctypes 模块调用动态链接库,如何传入一个结构体指针

最近用 dv2xvid 这个东东很多,上两周几乎每天都用它跑一个晚上压缩2个小时的视频。于是又萌发了把它改进得更通用的念头。

目前 dv2xvid 有一个很严重的问题,就是只支持 xvid-1.1.0-beta2 的压缩。而事实上目前大家用的最多的是应该都是正式版本,比如 1.0.3 或者 1.1.0 之类。如果想能支持更多版本的 xvid codec,就必须能在压缩之前判断 xvid 的版本。

恶心的是安装的 xvid 的目标文件没有 Windows Dll 的版本属性,查了半天,调用 xvidcore.dll 里面的一个函数可以获得 xvidcore.dll 的版本号

#include "xvid.h"

{
  xvid_gbl_info_t info;
  HINSTANCE m_hdll;

  memset(&info, 0, sizeof(info));
  info.version = XVID_VERSION;
  m_hdll = LoadLibrary(XVID_DLL_NAME);
  if (m_hdll != NULL) {
    ((int (__cdecl *)(void *, int, void *, void*))
GetProcAddress(m_hdll, "xvid_global"))(0, XVID_GBL_INFO, &info, NULL);
    
   printf("xvidcore.dll version %d.%d.%d (\"%s\")",
                XVID_VERSION_MAJOR(info.actual_version),
                XVID_VERSION_MINOR(info.actual_version),
                XVID_VERSION_PATCH(info.actual_version),
                info.build);

    FreeLibrary(m_hdll);
  } else {
    printf("xvidcore.dll not found!");
  }
}

如果在 python 里面做到这个事情,可以通过 ctypes 模块来完成。但查遍 ctypes 有关的中文文档,都没有关于怎样在函数中传入结构体指针的说明,只能自己 google 之,后来发现应该这么来做:

from ctypes import *

### 定义结构体
class xvid_gbl_info_t(Structure):
    _fields_ = [("version", c_int),
                ("actual_version", c_int),
                ("build", c_char_p),
                ("cpu_flags", c_uint),
                ("num_threads", c_int)]

XVID_GBL_INFO = 1

dll = cdll.load("c:\\windows\\system32\\xvidcore.dll")
xvid_global = dll.xvid_global

### 构造 pinfo 结构体, 然后赋值
pinfo = xvid_gbl_info_t()
pinfo.version = ((((1)&0xff)<<16) | (((0)&0xff)<<8) | ((0)&0xff))

x = c_voidp(0)
y = c_voidp(0)
### 用 byref 传入指针
if xvid_global(x, c_int(XVID_GBL_INFO), byref(pinfo), y) == 0:
    major_version = (pinfo.actual_version>>16)&0xff
    minor_version = (pinfo.actual_version>>8)&0xff
    patch_version = (pinfo.actual_version>>0)&0xff
    print major_version, minor_version, patch_version
    print pinfo.build
    print pinfo.cpu_flags
    print pinfo.num_threads
else:
    print "ERROR"

分享到:
评论

相关推荐

    ctypes--Python调用c接口.pdf

    它是一个外部函数库,为Python提供了与C语言兼容的数据类型,并允许Python代码调用动态链接库(DLLs)或共享库中的函数。通过ctypes模块,可以将这些库封装在纯Python代码中,无需编写额外的C代码。 标签“python c...

    python-ctypes模块中文帮助文档.docx

    `ctypes`模块在Python中主要用于加载和调用C语言编写的共享库(动态链接库)。无论是Windows下的`.dll`文件还是Linux下的`.so`文件,都可以通过`ctypes`进行加载。 **1.1 加载方式** - **在Windows上**: - 使用`...

    使用c lib的python模块ctypes

    Python中的`ctypes`模块是Python标准库的一部分,它允许我们直接在Python代码中调用C语言编写的动态链接库(DLLs on Windows,.so files on Linux等)。这个功能对于那些希望利用C库的强大功能,同时又不想或不能...

    python ctypes 中文帮助

    Python的ctypes模块是Python与C语言库交互的重要工具,它允许Python程序调用C编写的动态链接库(DLL)中的函数。ctypes提供了一种简单的方法,将Python对象转换为C数据类型,并且可以调用C库中的函数,使得Python...

    python-ctypes模块中文帮助文档重难点.pdf

    Python的ctypes模块是用于在Python中调用C语言编写的动态链接库(DLL)的关键工具。ctypes提供了与C语言接口的桥梁,使得Python程序员可以轻松地调用C库中的函数,处理C的数据类型,并进行类型转换。以下是对ctypes...

    python-ctypes模块中文帮助文档.pdf

    Python的ctypes模块是Python与C语言库交互的重要工具,它允许Python程序调用C语言编写的动态链接库(DLL)。ctypes提供了一种灵活的方式,使得Python开发者可以使用C语言级别的接口来调用底层操作系统功能或者第三方库...

    Python调用DLL文件.pdf

    - ctypes是Python标准库中的一个模块,它提供和C语言兼容的数据类型,并允许调用动态链接库中的函数。 - 在Python脚本中,首先需要导入ctypes模块,然后通过适当的函数加载DLL文件,并通过函数指针调用其中的函数...

    07-python-生成编译注释-ctypes

    `ctypes`是Python的标准库之一,它提供了一种方式来调用C语言编写的动态链接库(DLLs on Windows, shared libraries on Unix/Linux)中的函数,使得Python代码能够直接操作C级别的数据类型。 **一、ctypes简介** `...

    python使用ctypes调用扩展模块的实例方法

    Python中的ctypes库是用于调用C语言编写的动态链接库(DLL)或共享对象(SO)的关键工具,使得Python程序能够与C代码交互,从而提高执行效率并解决全局解释器锁(GIL)带来的多线程限制。GIL使得Python在多线程环境...

    python调用C的例子

    这里,`CDLL`是`ctypes`模块中的一个类,用于加载动态链接库并提供了一个接口去调用其中的函数。 ### 知识点四:调用C函数 一旦DLL被加载到Python环境中,就可以像调用普通Python函数一样调用C函数了。但在调用前...

    Python调用C代码的方案调研

    - 在Windows平台上,动态链接库(DLL)文件通常以`.dll`为扩展名。 - 在Linux环境下,则通常使用`.so`扩展名的共享对象文件。 - 加载动态库的方法包括: - `ctypes.cdll.LoadLibrary(dllpath)`:用于加载C调用...

    基于Python与海康SDK的工业设备视频监控系统开发.pdf

    开发过程中使用的Ctypes模块是Python内置的模块,它允许Python程序调用动态链接库(DLL)中的函数,从而实现了Python与C语言等其他语言编写的程序之间的接口。使用Ctypes模块时,可以通过ctypes.windll.loadLibrary...

    Python调用C++几种常用使用方法

    Python 标准库中的 ctypes 模块允许直接调用 C 兼容的动态链接库(DLL 或 SO),因此也可以用来调用 C++ 代码。基本类型和字符串可以通过 ctypes 的数据类型映射,结构体则需要定义对应的 Python 类,并使用 `...

    python控制数据采集器USB5538(csdn)————程序.pdf

    ctypes是一个标准库,它允许Python代码直接调用C编译的动态链接库。要使用USB5538的DLL,我们首先需要导入ctypes库,然后使用`ctypes.windll.LoadLibrary()`函数加载DLL文件。例如: ```python import ctypes # ...

    python3利用ctypes传入一个字符串类型的列表方法

    为了让 Python 可以调用这段 C 语言代码,我们需要将它编译成一个动态链接库(.so 文件)。编译命令如下: ```bash gcc -o hello1.so -shared -fPIC c_p.c ``` 这里的 `-shared` 表示生成共享对象文件,`-fPIC` ...

Global site tag (gtag.js) - Google Analytics