Solved

How do I call GetPerAdapterInfo from Visual Basic 6

Posted on 2009-04-15
2
578 Views
Last Modified: 2012-05-06
I have some experience with Visual Basic 6 and a good amount of experience with C/C++ .  I have been trying to get some basic Network Adapter information (the code has to be VB6), and I have gotten some of the way there.  

However I have spent many hours on this and I still cannot call the function GetPerAdapterInfo.  
I have managed to call the function GetAdaptersInfo which is very similar however I still cannot call GetPerAdapterInfo. Every time I call the function GetPerAdapterInfo I get a 232 error (ERROR_NO_DATA).  This happens the first time I call the function with a buffer length of 0.

I have passed in the indices from IP_ADAPTER_INFO and I have also entered these indices manually but I always get the same 232 error.  The indices for my network adapters are 2-4.  I have written the equivalent code in c++ with indices 2-4 and it works flawlessly.  However I have no idea what could be wrong with the vb6 code.

The very first call to GetPerAdapterInfo to get the correct buffer size fails with error 232.  I have looked at the sizes of the various structures such as IP_ADAPTER_INFO and they are exactly the same size as in my C++ code.

Any help/suggestions would be very appreciated.
Private Declare Function GetNetworkParams Lib "IPHlpApi.dll" _
       (FixedInfo As Any, pOutBufLen As Long) As Long
Private Declare Function GetAdaptersInfo Lib "IPHlpApi.dll" _
       (IpAdapterInfo As Any, pOutBufLen As Long) As Long
Private Declare Function GetPerAdapterInfo Lib "IPHlpApi.dll" _
       (IfIndex As Long, pPerAdapterInfo As Any, pOutBufLen As Long) As Long
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" _
       (Destination As Any, Source As Any, ByVal Length As Long)
 
Private Type IP_ADDR_STRING
            Next As Long
            IpAddress As String * 16
            IpMask As String * 16
            Context As Long
End Type
 
Private Type IP_PER_ADAPTER_INFO
            AutoconfigEnabled As Long
            AutoconfigActive As Long
            CurrentDnsServer As Long
            DnsServerList As IP_ADDR_STRING
End Type
 
Private Type IP_ADAPTER_INFO
            Next As Long
            ComboIndex As Long
            AdapterName As String * MAX_ADAPTER_NAME_LENGTH
            Description As String * MAX_ADAPTER_DESCRIPTION_LENGTH
            AddressLength As Long
            Address(MAX_ADAPTER_ADDRESS_LENGTH - 1) As Byte
            Index As Long
            Type As Long
            DhcpEnabled As Long
            CurrentIpAddress As Long
            IpAddressList As IP_ADDR_STRING
            GatewayList As IP_ADDR_STRING
            DhcpServer As IP_ADDR_STRING
            HaveWins As Long
            PrimaryWinsServer As IP_ADDR_STRING
            SecondaryWinsServer As IP_ADDR_STRING
            LeaseObtained As Long
            LeaseExpires As Long
End Type
 
Public Function HasDNS(Index As Long) As Boolean
    Dim error As Long
    Dim DNSInfoBuffer() As Byte
    Dim DNSInfoSize As Long
    Dim DNSInfo As IP_PER_ADAPTER_INFO
    Dim NumStructs As Integer
    Dim DNSInfoPtr As Long
    Dim CurrDNSString As String
    Dim i As Integer
    
    DNSInfoSize = 0
    error = GetPerAdapterInfo(Index, ByVal 0&, DNSInfoSize)
    If error <> 0 Then
        If error <> ERROR_BUFFER_OVERFLOW Then
           HasDNS = False
           Exit Function
        End If
    End If
    ReDim DNSInfoBuffer(DNSInfoSize - 1)
 
    error = GetPerAdapterInfo(Index, DNSInfoBuffer(0), DNSInfoSize)
    If error <> 0 Then
       HasDNS = False
       Exit Function
    End If
   
    NumStructs = DNSInfoSize / Len(DNSInfo)
    DNSInfoPtr = VarPtr(DNSInfoBuffer(0))
 
    If (DNSInfoPtr = 0) Then
       HasDNS = False
       Exit Function
    End If
 
    CopyMemory DNSInfo, ByVal DNSInfoPtr, Len(DNSInfo)
        
    CurrDNSString = ZTrim(DNSInfo.DnsServerList.IpAddress)
    
    If (LenB(CurrDNSString) <> 0) Then
        HasDNS = True
    Else
        HasDNS = False
    End If
End Function

Open in new window

0
Comment
Question by:limemac85
2 Comments
 
LVL 16

Accepted Solution

by:
HooKooDooKu earned 500 total points
ID: 24157751
In VB6, unless a function parameter is specifically declared with ByVal, then ByRef is assumed and every parameter gets passed as a pointer.  That means in your declaration for GetPerAdapterInfo, it thinks all three parameters are pointers.

But programmer experience and instinct tell me that the 1st parameter is likely supposed to be the index VALUE rather than a pointer to the index variable.

If so, then you need to change the declaration for the function like this...

Private Declare Function GetPerAdapterInfo Lib "IPHlpApi.dll" _
(ByVal IfIndex As Long, ByRef pPerAdapterInfo As Any, ByRef pOutBufLen As Long) As Long

Note that the two ByRef are not required (because without ByVal, ByRef is assumed).  But I like to include it went calling Lib functions to help make it obvious where values are needed and where pointers are needed.
0
 

Author Closing Comment

by:limemac85
ID: 31570443
Thank you ! That was it.  I did not even realize the index was being passed by reference instead of by value.
0

Featured Post

Live: Real-Time Solutions, Start Here

Receive instant 1:1 support from technology experts, using our real-time conversation and whiteboard interface. Your first 5 minutes are always free.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Introduction While answering a recent question (http://www.experts-exchange.com/Q_27402310.html) in the VB classic zone, I wrote some VB code in the (Office) VBA environment, rather than fire up my older PC.  I didn't post completely correct code o…
I was working on a PowerPoint add-in the other day and a client asked me "can you implement a feature which processes a chart when it's pasted into a slide from another deck?". It got me wondering how to hook into built-in ribbon events in Office.
Show developers how to use a criteria form to limit the data that appears on an Access report. It is a common requirement that users can specify the criteria for a report at runtime. The easiest way to accomplish this is using a criteria form that a…
This lesson covers basic error handling code in Microsoft Excel using VBA. This is the first lesson in a 3-part series that uses code to loop through an Excel spreadsheet in VBA and then fix errors, taking advantage of error handling code. This l…

813 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

12 Experts available now in Live!

Get 1:1 Help Now