Sacha Barberが提供するコードを使用して、ネットワーク上のすべての PC のすべてのコンピューター名を取得しようとしています。元記事へのリンクはこちら. コードはもともと C# でしたが、VB に変換しました。Visual Studio からデバッグ モードでプログラムを実行すると、通常 (常にではありません) 正常に実行されますが、プログラムを展開すると、ほとんど実行されません。
次の行で失敗します。
Dim svrInfo As _SERVER_INFO_100 = DirectCast(Marshal.PtrToStructure(tmpBuffer, _
GetType(_SERVER_INFO_100)), _SERVER_INFO_100)
次のエラーが表示されます。
タイプ 'System.ExecutionEngineException' の未処理の例外が mscorlib.dll で発生しました HResult=-2146233082
メモリ割り当てと関係があることは知っていますが、このエラーを回避する方法がわかりません。Debug Diagnostics Tool 1.2 を使用してみましたが、それでも何を探すべきかわかりません。
Imports System.Runtime.InteropServices
Public Class NetworkInfo
Dim CurrentDomain As AppDomain = AppDomain.CurrentDomain
'import the NetServerEnum function from the netapi32.dll
Private Declare Unicode Function NetServerEnum Lib "netapi32" _
(ByVal Servername As IntPtr, _
ByVal Level As Integer, _
ByRef bufptr As IntPtr, _
ByVal PrefMaxLen As Integer, _
ByRef entriesread As Integer, _
ByRef TotalEntries As Integer, _
ByVal serverType As Integer, _
ByVal Domain As IntPtr, _
ByVal ResumeHandle As IntPtr) As Integer
'import the NetApiBufferFree function from the netapi32.dll
Private Declare Unicode Function NetApiBufferFree Lib "netapi32.dll" _
(ByRef buffer As IntPtr) As UInteger
Public Structure _SERVER_INFO_100
Friend sv100_platform_id As Integer
<MarshalAs(UnmanagedType.LPWStr)> _
Friend sv100_name As String
End Structure
Public Function GetNetworkComputers() As ArrayList
Dim networkComputers As New ArrayList()
Const MAX_PREFERRED_LENGTH As Integer = -1
Dim SV_TYPE_WORKSTATION As Integer = 1
Dim SV_TYPE_SERVER As Integer = 2
Dim buffer As IntPtr = IntPtr.Zero
Dim tmpBuffer As IntPtr = IntPtr.Zero
Dim entriesRead As Integer = 0
Dim totalEntries As Integer = 0
Dim resHandle As Integer = 0
Dim sizeofINFO As Integer = Marshal.SizeOf(GetType(_SERVER_INFO_100))
Try
Dim ret As Integer = NetServerEnum(Nothing, 100, buffer, MAX_PREFERRED_LENGTH, entriesRead, totalEntries, _
SV_TYPE_WORKSTATION Or SV_TYPE_SERVER, Nothing, resHandle)
If ret = 0 Then
For i As Integer = 0 To totalEntries
tmpBuffer = New IntPtr(CType(buffer, Long) + (i * sizeofINFO))
Dim svrInfo As _SERVER_INFO_100 = DirectCast(Marshal.PtrToStructure(tmpBuffer, _
GetType(_SERVER_INFO_100)), _SERVER_INFO_100)
networkComputers.Add(svrInfo.sv100_name)
Next
End If
Catch ex As Exception
Console.WriteLine("Error getting network computers.")
Finally
NetApiBufferFree(buffer)
End Try
Return networkComputers
End Function
End Class