我有一个具有以下功能的DLL,正在我的应用程序中使用
WritetoBuffer(BYTE* pBuffer, DATA_TYPE Type);
这是VB 6中使用的代码
Dim pBuffer() as byte
ReDim pBuffer(0 To (300 * 400 * 3 - 1))
Dim ppBuf As Long
ppBuf = VarPtr(pImageBuffer(0))
Dim Rtn As Integer
Rtn = WritetoBuffer(ppBuf, 1)
我正在尝试在VB.NET中编写等效代码,但我遇到了困难。尝试使用以下功能,但它无法正常工作。
Public Function VarPtr(ByVal e As Object) As Intptr
Dim GC As GCHandle = GCHandle.Alloc(e, GCHandleType.Pinned)
Dim GC2 As Intptr = GC.AddrOfPinnedObject.ToInt32
GC.Free()
Return GC2
End Function
之前我没有使用Marshal Class或类似的功能,我不确定正确的方法。有人可以就此提出建议吗?
答案 0 :(得分:2)
正如@Dai评论的那样,.ToInt32
在这里不正确,在使用之前你无法释放句柄。
Dim pBuffer(300 * 400 * 3 - 1) As Byte
Dim pinned = GCHandle.Alloc(pBuffer, GCHandleType.Pinned)
Dim Rtn As Integer = WritetoBuffer(pinned.AddrOfPinnedObject(), 1)
pinned.Free()
答案 1 :(得分:0)
试试这个。当你打电话时,你需要GCHandle才能保持活力。仅根据我的理解返回指针的地址是不够的。当你完成后,释放手柄。
Dim Handle As GCHandle = GCHandle.Alloc(pBuffer, GCHandleType.Pinned)
Dim ppbuf As IntPtr = Handle.AddrOfPinnedObject.ToInt32
Dim Rtn As Integer
Rtn = WritetoBuffer(ppbuf, 1)
Handle.Free()
答案 2 :(得分:-1)
在这种情况下,您不需要获取字节数组的指针。由于BYTE* pBuffer
被用作数组,因此您只需要在VB.NET中使用它。
因此你可以像这样声明你的P / Invoke:
<DllImport("yourfile.dll")> _
Public Shared Function WritetoBuffer(ByVal pBuffer As Byte(), ByVal Type As Integer) As Integer
End Function
...然后像这样使用它:
Dim pBuffer() as byte
ReDim pBuffer(0 To (300 * 400 * 3 - 1))
Dim Rtn As Integer = WritetoBuffer(pBuffer, 1)