0

我正在使用 Python 并安装了最新版本的 NI-VISA。我正在使用 ctypes 包来加载使用 NI-VISA 安装的 visa32.dll。

我使用了 NI-VISA 文档以及以下页面作为我的代码的基础。

我已经知道 pyVisa 包装器,并且使用他们的 find_resources 函数确实会返回连接的仪器。但是,我不想使用这个包装器,而是直接使用 VISA DLL 文件。

我也一直在浏览 pyVisa 代码,看看他们是如何做到的,并试图从中学习,但似乎我仍然不明白。

这是我当前未完成的代码:

import sys
from ctypes import *
visa = windll.LoadLibrary("visa32.dll")

resourceManagerHandle = c_int(0)
visa.viOpenDefaultRM(byref(resourceManagerHandle))

instr_list = c_ulong(0)
nb = c_ulong(0)
desc = create_string_buffer(128)

print(visa.viFindRsrc(resourceManagerHandle,
                      "?*INSTR",
                      byref(instr_list),
                      byref(nb),
                      byref(desc)))
# The previous line prints: -1073807343

print(instr_list)
# The previous line prints: c_ulong(0)

我一直试图在 Internet 上查找错误代码 -1073807343(十六进制为 4000FFEF)的含义,虽然我在 National Instruments 论坛上找到了一些关于它的论坛帖子,但我仍然不太明白它的含义。

我欢迎任何建议、指导或相关信息的链接。

4

1 回答 1

1

文字"?*INSTR"创建一个str对象,在 Python 3 中是 Unicode。 ctypes 将 unicode 字符串转换为wchar_t *. 在 Windows 上,wchar_t是 2 个字节,因此 ctypes 传递一个指向 UTF-16 编码缓冲区的指针"?\x00*\x00I\x00N\x00S\x00T\x00R\x00"。请记住,该函数需要一个以 null 结尾的字符串。

要改为传递字节字符串,请在文字前面加上前缀b以创建bytes对象,即使用b"?*INSTR".

为了防止这样的错误被忽略,定义函数指针的argtypes. 如果为定义为的参数传递ArgumentError了 unicode参数, ctypes 将引发.strc_char_p

from ctypes import *

visa = WinDLL("visa32.dll") # or windll.visa32

def vi_status_check(vi_status, func, args):
    if vi_status < 0:
        raise RuntimeError(hex(vi_status + 2**32))
    return args

visa.viOpenDefaultRM.errcheck = vi_status_check
visa.viOpenDefaultRM.argtypes = [POINTER(c_uint32)]
visa.viFindRsrc.errcheck = vi_status_check
visa.viFindRsrc.argtypes = [c_uint32,          # sesn
                            c_char_p,          # expr
                            POINTER(c_uint32), # findList
                            POINTER(c_uint32), # retcnt
                            c_char_p]          # desc

rm_session = c_uint32()
visa.viOpenDefaultRM(byref(rm_session))

expr = b"?*INSTR"    
instr_list = c_uint32()
nb = c_uint32()
desc = create_string_buffer(256)

visa.viFindRsrc(rm_session,
                expr,
                byref(instr_list),
                byref(nb),
                desc)

NI-VISA 程序员参考手册在第5-30 页上说instrDesc应该至少有 256 个字节。

于 2014-03-11T16:24:58.487 回答