Python 如何找到使用ctypes从DLL文件导入的函数所需的参数?

Python 如何找到使用ctypes从DLL文件导入的函数所需的参数?,python,pass-by-reference,ctypes,python.net,Python,Pass By Reference,Ctypes,Python.net,我正在尝试使用Maxon提供的库运行一些电机控制器。这个库是一个DLL文件,我正在使用ctypes和pythonNet阅读它。图书馆正在工作,我可以驱动电机,到目前为止我使用的大多数功能都很好。但是,要从控制器读回位置数据,我需要使用一个名为VcsGetObject的函数。我对函数的每次调用都会导致错误,因为我没有正确的输入或输出: TypeError:没有方法与VcsGetObject的给定参数匹配 VcsGetObject函数接受通过引用输入的数据,并通过该变量返回位置数据。我尝试过各种方法

我正在尝试使用Maxon提供的库运行一些电机控制器。这个库是一个DLL文件,我正在使用ctypes和pythonNet阅读它。图书馆正在工作,我可以驱动电机,到目前为止我使用的大多数功能都很好。但是,要从控制器读回位置数据,我需要使用一个名为VcsGetObject的函数。我对函数的每次调用都会导致错误,因为我没有正确的输入或输出:

TypeError:没有方法与VcsGetObject的给定参数匹配

VcsGetObject函数接受通过引用输入的数据,并通过该变量返回位置数据。我尝试过各种方法将数据传递给函数,但还没有成功。我已经尝试过给函数额外的输出,因为我已经读到PythonNet可以自动完成。我尝试过传入元组或列表,或者使用ctypes.byref()传递ctypes数据类型

老实说,我不确定问题出在哪里,我想知道是否有某种方法可以查看函数在中的期望值。我有C++函数的文档,但是因为我从DLL导入它,所以我不能真正地知道问题在哪里。我为这个问题的模糊性道歉,我真的觉得有很多地方可能会出错,但也许有一些很明显的事情我只是不知道

import time
import clr #pythonnet, manually installed with a downloaded wheel and pip
import ctypes #module to open dll files
import System
clr.AddReference('EposCmd.Net')
EposCmd64 = ctypes.CDLL('.\EposCmd64.dll')
from EposCmd.Net.VcsWrapper import Device

print("START")
print()

Device.Init()
nodeID = 1
baudrate = 1000000
timeout = 500
errorCode = 0
index = int('0x606C',16)
subindex = 0
dataLength = 4

# These functions all work as expected, so the library is being imported correctly
keyHandle, error = Device.VcsOpenDevice('EPOS4', 'MAXON SERIAL V2', 'USB', 'USB0', errorCode) #opens EPOS
print(errorCode)
Device.VcsSetProtocolStackSettings(keyHandle, baudrate, timeout, errorCode) #set baudrate
Device.VcsClearFault(keyHandle, nodeID, errorCode) #clear all faults

# # Trying to use lists or tuples doesn't work
#data = [0]
#readLength = [0]
#output = Device.VcsGetObject(keyHandle,nodeID,index,subindex,data,readLength,errorCode)

# # Using ctypes and .byref(), also doesn't work
#data = ctypes.c_byte()
#readLength = ctypes.c_byte()
#output = Device.VcsGetObject(keyHandle,nodeID,index,subindex,ctypes.byref(data),ctypes.byref(readLength),errorCode)

# # Trying to use PythonNet to turn by ref inputs into outputs
output, data, readLength = Device.VcsGetObject(keyHandle,nodeID,index,subindex,errorCode)
#print(data)
#print(readLength)
我已经包括了maxon文档的链接,GetObject在第4.1.4节中。
首先,函数调用看起来不正确。这是未经测试的,但您的开放设备调用应该更像:

from ctypes import byref, c_byte, c_void_p
from ctypes.wintypes import WORD, DWORD

# Set type
errorCode = DWORD()

# Pass error by reference
handle = Device.VcsOpenDevice(
    'EPOS4',
    'MAXON SERIAL V2',
    'USB',
    'USB0',
    byref(errorCode))

# Read error code after function call
print(errorCode.value)
根据您链接的文档
VCS\u GetObject
如下所示:

nodeId = WORD(1)
objectIndex = WORD(0x606C)
objectSubIndex = c_byte(0)
NbOfBytesToRead = DWORD(
data = c_void_p()
# Vary this to read more or less data
NbOfBytesToRead = DWORD(4)
NbOfBytesRead = DWORD()
errorCode = DWORD()

return_value = Device.VcsGetObject(
    handle,
    nodeId,
    objectIndex,
    objectSubIndex,
    byref(data),
    NbOfBytesToRead,
    byref(NbOfBytesRead),
    byref(errorCode))

print(errorCode.value)

您还应该设置restype和argtypes。

首先,您的函数调用看起来不正确。这是未经测试的,但您的开放设备调用应该更像:

from ctypes import byref, c_byte, c_void_p
from ctypes.wintypes import WORD, DWORD

# Set type
errorCode = DWORD()

# Pass error by reference
handle = Device.VcsOpenDevice(
    'EPOS4',
    'MAXON SERIAL V2',
    'USB',
    'USB0',
    byref(errorCode))

# Read error code after function call
print(errorCode.value)
根据您链接的文档
VCS\u GetObject
如下所示:

nodeId = WORD(1)
objectIndex = WORD(0x606C)
objectSubIndex = c_byte(0)
NbOfBytesToRead = DWORD(
data = c_void_p()
# Vary this to read more or less data
NbOfBytesToRead = DWORD(4)
NbOfBytesRead = DWORD()
errorCode = DWORD()

return_value = Device.VcsGetObject(
    handle,
    nodeId,
    objectIndex,
    objectSubIndex,
    byref(data),
    NbOfBytesToRead,
    byref(NbOfBytesRead),
    byref(errorCode))

print(errorCode.value)
您还应该设置restype和argtypes