我正在 VB.NET 中开发一个应用程序(针对使用 FTDI USB 串行芯片的硬件的客户。通信使用 FTD2XX 库和相应的 Nuget 包(FTD2XX.Net v1.2.1)。在 Visual Studio 进行一些更新后(可能更新到17.1,但我不确定)除了少数几个功能外,所有功能都停止工作。当前 VS 版本是 17.1.1。 例如,可以获得 FTDI 驱动程序连接的设备数量:
Friend Declare Function FT_CreateDeviceInfoList Lib "FTD2XX.DLL" (ByRef lngNumDevs As Integer) As Integer
...
Dim ftStatus As Integer
Dim numDevices As Integer
ftStatus = FT_CreateDeviceInfoList(numDevices)
在上面的代码片段中,ftStatus 结果 = 0(即正常)并且
numDevices
设置为 1(正确)。
当我想做一些严肃的事情时,问题就开始了:
Friend Declare Function FT_GetComPortNumber Lib "FTD2XX.DLL" (ByVal lnghandle As Integer, ByRef lplComPortNumber As Integer) As Integer
Friend Declare Function FT_Open Lib "FTD2XX.DLL" (ByVal iDevice As Integer, ByRef lnghandle As Integer) As Integer
Friend Declare Function FT_Close Lib "FTD2XX.DLL" (ByVal lnghandle As Integer) As Integer
Dim portHandle as Integer
Dim cpNumber as Long
For i% = 0 To 255
ftStatus = FT_Open(i, portHandle)
If ftStatus = FT_OK Then
ftStatus = FT_GetComPortNumber(portHandle, cpNumber)
ftStatus = FT_Close(portHandle)
' here is some non-essential code registering that port at index i% exists...
End If
Next
在上面的代码中,FT_Open 返回
ftStatus = 0
(FT_OK) 并为 portHandle
设置一个值。
但是,下一个调用
FT_GetComPortNumber
返回ftStatus = 1
(FT_INVALID_HANDLE),并且传递给cpNumber
的值是0xFFFF(显示为正数,但实际上应该是-1,我猜......)。更糟糕的是,FT_Close()
也返回FT_INVALID_HANDLE
并且端口保持开放状态。我通过尝试从另一个应用程序打开端口来验证它 - 访问被拒绝。
有时,尽管如此混乱,
FT_Write
和FT_Read
功能似乎仍然可以工作,但在我最后一次尝试中,我根本无法与硬件进行任何通信。
我尝试使用
System.IO.Ports.SerialPort
作为可能的解决方法,但这根本不起作用。最重要的是,我需要在 RTS 上使用 bit-bang,因为它控制电源电压和连接到 FTDI 芯片另一侧的硬件的复位。如果无法将 RTS 关闭数百毫秒然后一直保持下去,我就无法控制硬件。 AFAIK System.IO.Ports.SerialPort
不可能做到这一点。
解决办法是什么?
@HansPassant 写道:
声明有误,一定是
lnghandle As IntPtr
。当您在 64 位模式下运行应用程序时,Integer
和 IntPtr
之间的区别很重要。当针对 .NETCore 时很容易发生,就像在 VS2022 中一样。
--汉斯·帕桑特
现在可以了。我要做的就是将 porthandle 声明更改为 long。
Dim portHandle As Long
对我来说这仍然不起作用。
`
进口系统 导入 System.Threading 导入 System.IO.Ports
模块模块1
Private Declare Function FT_CreateDeviceInfoList Lib "FTD2XX.DLL" (ByRef lngNumDevs As Integer) As Integer
Private Declare Function FT_GetComPortNumber Lib "FTD2XX.DLL" (ByVal lnghandle As IntPtr, ByRef lplComPortNumber As Integer) As Integer
Private Declare Function FT_Open Lib "FTD2XX.DLL" (ByVal iDevice As Integer, ByRef lnghandle As IntPtr) As Integer
Private Declare Function FT_Close Lib "FTD2XX.DLL" (ByVal lnghandle As IntPtr) As Integer
Sub Main()
Dim portHandle As Integer
Dim cpNumber As Long
Dim ftoStatus As Integer
Dim ftcStatus As Integer
Dim ftpStatus As Integer
ftoStatus = FT_Open(0, portHandle)
Console.WriteLine("FT_Open Status: " & ftoStatus)
Console.WriteLine("PortHandle: " & portHandle)
If ftoStatus = 0 Then
ftpStatus = FT_GetComPortNumber(portHandle, cpNumber)
Console.WriteLine("FT_GetComPortNumber Status: " & ftpStatus)
Console.WriteLine("COM Port Number: " & cpNumber)
ftcStatus = FT_Close(portHandle)
Console.WriteLine("FT_Close Status: " & ftcStatus)
End If
End Sub
结束模块`