python-3.x - 在 xlib 上使用 ctypes 时出现分段错误
问题描述
我正在尝试从 xlib 屏幕保护程序中获取空闲时间
我尝试调试它,错误开始在该行之后发生
dpy = xlib.XOpenDisplay(os.environ['DISPLAY'].encode('ascii'))
这是我的代码
class XScreenSaverInfo( ctypes.Structure):
""" typedef struct { ... } XScreenSaverInfo; """
_fields_ = [('window', ctypes.c_ulong), # screen saver window
('state', ctypes.c_int), # off,on,disabled
('kind', ctypes.c_int), # blanked,internal,external
('since', ctypes.c_ulong), # milliseconds
('idle', ctypes.c_ulong), # milliseconds
('event_mask', ctypes.c_ulong)] # events
xlib = ctypes.cdll.LoadLibrary('libX11.so')
dpy = xlib.XOpenDisplay(os.environ['DISPLAY'].encode('ascii'))
root = xlib.XDefaultRootWindow(dpy)
xss = ctypes.cdll.LoadLibrary( 'libXss.so')
xss.XScreenSaverAllocInfo.restype = ctypes.POINTER(XScreenSaverInfo)
xss_info = xss.XScreenSaverAllocInfo()
xss.XScreenSaverQueryInfo( dpy, root, xss_info)
print("Idle time in milliseconds: %d") % xss_info.contents.idle
我得到一个Segmentation fault (core dumped)
错误。请帮忙:)
解决方案
错误是因为未指定argtypes (和restype ),如[Python 3.Docs]: ctypes - Specifying the required argument types (function prototypes)中所述。在这种情况下发生的事情有很多例子,这里有两个:
- [SO]:不同操作系统上的 python ctypes 问题(@CristiFati 的回答)
- [SO]:Python ctypes cdll.LoadLibrary,实例化一个对象,执行它的方法,私有变量地址被截断(@CristiFati 的回答)
在调用它之前为每个函数声明它们:
xlib.XOpenDisplay.argtypes = [ctypes.c_char_p]
xlib.XOpenDisplay.restype = ctypes.c_void_p # Actually, it's a Display pointer, but since the Display structure definition is not known (nor do we care about it), make it a void pointer
xlib.XDefaultRootWindow.argtypes = [ctypes.c_void_p]
xlib.XDefaultRootWindow.restype = ctypes.c_uint32
xss.XScreenSaverQueryInfo.argtypes = [ctypes.c_void_p, ctypes.c_uint32, ctypes.POINTER(XScreenSaverInfo)]
xss.XScreenSaverQueryInfo.restype = ctypes.c_int
推荐阅读
- android - 在 ScrollView 上放置 Android 横幅广告
- html - 是否有一种仅 html + css 的方式来跨多个网格同步动态网格列宽?
- react-native - 从服务器加载反应本机包(尝试将其托管在 aws S3 上)用于 Android
- java - 将 sql 参数传递给 jdbcTemplate.query 时,我得到一个带有对象 args 的 SQLException
- python - 打印所有连续子数组
- git - 我可以将更新的分支合并到多个功能分支而不检查每个分支吗?
- javascript - Javascript数组json转换为父子json对象
- java - Talend 中的 tJava 和 tJavaRow 有什么区别?
- pandas - Groupby并连接多列
- python - 获得 seaborn.catplot 中计算的平均值的标准误差