Solved

Get Hostname using IP Address

Posted on 2000-05-14
6
3,418 Views
Last Modified: 2008-03-03
I need get hostname by giving IP address, like "xx.xx.xx.xx". I tried to use API gethostbyaddr, but I failed.
0
Comment
Question by:elchang
  • 3
  • 2
6 Comments
 
LVL 27

Accepted Solution

by:
Ark earned 80 total points
ID: 2809534
Hi
Here is code to convert "Dotted IP" to LongIP and host name and vise versa:

'---bas module code---

Option Explicit

Const SOCKET_ERROR = -1
Const INADDR_NONE = -1
Const PF_INET = 2

Private Type T_WSA
    wVersion As Integer
    wHighVersion As Integer
    szDescription(0 To 255) As Byte
    szSystemStatus(0 To 128) As Byte
    iMaxSockets As Integer
    iMaxUdpDg As Integer
    lpVendorInfo As Long
End Type

Private WSAData As T_WSA

Private IPAddress(3) As Byte

Type T_Host
    h_name As Long
    h_aliases As Long
    h_addrtype As Integer
    h_length As Integer
    h_addr_list As Long
End Type

Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (Dest As Any, Src As Any, ByVal cb&)

Private Declare Function gethostbyaddr Lib "wsock32.dll" (addr As Long, ByVal addr_len As Long, ByVal addr_type As Long) As Long
Private Declare Function gethostbyname Lib "wsock32.dll" (ByVal HostName As String) As Long
Private Declare Function inet_addr Lib "wsock32.dll" (ByVal addr As String) As Long
Private Declare Function WSAStartup Lib "wsock32.dll" (ByVal a As Long, b As T_WSA) As Long
Declare Function WSACleanUp Lib "wsock32.dll" Alias "WSACleanup" () As Integer

Function WinsockInit() As Boolean
    WinsockInit = Not WSAStartup(&H101, WSAData)
End Function

Function DNSToDottedIP(sHost As String) As String
    Dim p As Long
    Dim Host As T_Host
    Dim lpListAddress As Long
    Dim FirstAddress As Long
    Dim Address As Long

    sHost = sHost & String(64 - Len(sHost), 0)
    p = gethostbyname(sHost)
    If p = SOCKET_ERROR Then
        Exit Function
    Else
        If p <> 0 Then
            CopyMemory Host, ByVal p, Len(Host)
            lpListAddress = Host.h_addr_list
            DNSToDottedIP = ""
' Next three strings allow receive only first IP address
 CopyMemory FirstAddress, ByVal lpListAddress, 4
 CopyMemory Address, ByVal FirstAddress, 4
 DNSToDottedIP = LongIPToDotted(Address)
' *************
' One DNS can contain a list of IP. If you need all
' addresses, you can make a loop here, increasing
' lpListAddres by 4 every time
' If You want to do so, comment three strings above my comments
' and uncomment Loop below. You must change Multiline
' property of Text1(1) to True and add vertical scrollbar
' to see all addresses in this text box
' ************
' Do
'  CopyMemory FirstAddress, ByVal lpListAddress, 4
'  CopyMemory Address, ByVal FirstAddress, 4
'  If Address = 0 Then Exit Do
'  DNSToDottedIP = DNSToDottedIP & LongIPToDotted(Address) & vbCrLf
'  lpListAddress = lpListAddress + 4
' Loop
        Else
            DNSToDottedIP = "No DNS Entry"
        End If
    End If
End Function

Function DottedIPToDNS(ByVal sAddress As String) As String
    Dim lAddress As Long
    Dim p As Long
    Dim HostName As String
    Dim Host As T_Host

    lAddress = inet_addr(sAddress)
    p = gethostbyaddr(lAddress, 4, PF_INET)
    If p <> 0 Then
        CopyMemory Host, ByVal p, Len(Host)
        HostName = String(256, 0)
        CopyMemory ByVal HostName, ByVal Host.h_name, 256
        If HostName = "" Then
           DottedIPToDNS = "Unable to Resolve Address"
        Else
           DottedIPToDNS = Left(HostName, InStr(HostName, Chr(0)) - 1)
        End If
    Else
        DottedIPToDNS = "No DNS Entry"
    End If
End Function

Function DottedIPToLong(Address As String) As String
  Dim lTmp As Long
  lTmp = inet_addr(Address)
  If lTmp = INADDR_NONE Then
     DottedIPToLong = "Invalid Address"
  Else
     DottedIPToLong = CStr(lTmp)
  End If
End Function

Function LongIPToDotted(Address As Long) As String
  Dim i As Integer, sTmp As String
  sTmp = ""
  CopyMemory IPAddress(0), Address, 4
  For i = 0 To 3
    sTmp = sTmp & CStr(IPAddress(i)) & "."
  Next i
  LongIPToDotted = Left$(sTmp, Len(sTmp) - 1)
End Function

' --Form code --
(you need an array of textboxes (Text1(0),Text1(1),Text1(2)), same array of option buttons (option1(0)...), one lable and one command button:

Dim InputType As Integer
Dim DefText(2) As String

Private Sub Command1_Click()
   Me.MousePointer = vbHourglass
   If Not WinsockInit Then
      Me.MousePointer = 0
      MsgBox "Can not initialize Winsock. Check your connection", vbCritical
      WSACleanUp
      Exit Sub
   End If
   Dim i As Integer
   For i = 0 To 2
       Text1(i).Visible = True
   Next i
   Select Case InputType
          Case 0
               If Left$(Text1(0), 4) = "http" Then Text1(0) = Mid$(Text1(0), 8)
'               If Left$(Text1(0), 3) = "www" Then Text1(0) = Mid$(Text1(0), 5)
               Text1(1) = DNSToDottedIP(Text1(0))
               Text1(2) = DottedIPToLong(Text1(1))
          Case 1
               Text1(0) = DottedIPToDNS(Text1(1))
               Text1(2) = DottedIPToLong(Text1(1))
          Case 2
               Text1(1) = LongIPToDotted(Text1(2))
               Text1(0) = DottedIPToDNS(Text1(1))
   End Select
   WSACleanUp
   Me.MousePointer = 0
End Sub

Private Sub Form_Load()
   Me.Caption = "Address Converting"
   Option1(0).Caption = "DNS"
   Option1(1).Caption = "DottedIP"
   Option1(2).Caption = "LongIP"
   Label1 = "Input Address"
   Command1.Caption = "Convert address"
   DefText(0) = "altavista.com"
   DefText(1) = "204.71.200.243"
   DefText(2) = "1906196696"
   For i = 0 To 2
      Text1(i).Text = ""
   Next i
   Option1(0).Value = True
End Sub

Private Sub Option1_Click(Index As Integer)
  InputType = Index
  For i = 0 To 2
      Text1(i).Visible = Option1(i).Value
  Next i
  If Text1(Index) = "" Then Text1(Index) = DefText(Index)
End Sub

Cheers
0
 
LVL 27

Expert Comment

by:Ark
ID: 2809586
Hi

Remove some code, now exactly what you want:

Option Explicit

Const PF_INET = 2

Private Type T_WSA
    wVersion As Integer
    wHighVersion As Integer
    szDescription(0 To 255) As Byte
    szSystemStatus(0 To 128) As Byte
    iMaxSockets As Integer
    iMaxUdpDg As Integer
    lpVendorInfo As Long
End Type

Private WSAData As T_WSA

Private IPAddress(3) As Byte

Type T_Host
    h_name As Long
    h_aliases As Long
    h_addrtype As Integer
    h_length As Integer
    h_addr_list As Long
End Type

Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (Dest As Any, Src As Any, ByVal cb&)

Private Declare Function gethostbyaddr Lib "wsock32.dll" (addr As Long, ByVal addr_len As Long, ByVal addr_type As Long) As Long
Private Declare Function inet_addr Lib "wsock32.dll" (ByVal addr As String) As Long
Private Declare Function WSAStartup Lib "wsock32.dll" (ByVal a As Long, b As T_WSA) As Long
Private Declare Function WSACleanUp Lib "wsock32.dll" Alias "WSACleanup" () As Integer

Private Function WinsockInit() As Boolean
    WinsockInit = Not WSAStartup(&H101, WSAData)
End Function

Private Function DottedIPToDNS(ByVal sAddress As String) As String
   DottedIPToDNS = ""
   If Not WinsockInit Then
      MsgBox "Can not initialize Winsock. Check your connection", vbCritical
      WSACleanUp
      Exit Function
   End If
    Dim lAddress As Long
    Dim p As Long
    Dim HostName As String
    Dim Host As T_Host

    lAddress = inet_addr(sAddress)
    p = gethostbyaddr(lAddress, 4, PF_INET)
    If p <> 0 Then
        CopyMemory Host, ByVal p, Len(Host)
        HostName = String(256, 0)
        CopyMemory ByVal HostName, ByVal Host.h_name, 256
        If HostName = "" Then
           DottedIPToDNS = "Unable to Resolve Address"
        Else
           DottedIPToDNS = Left(HostName, InStr(HostName, Chr(0)) - 1)
        End If
    Else
        DottedIPToDNS = "No DNS Entry"
    End If
    WSACleanUp
End Function

' Using:
' text1.text= DottedIPToDNS(208.50.148.12)
'return value - expert-exchange.com

Cheers
0
 
LVL 6

Expert Comment

by:setiawan
ID: 2809722
Private Const WSADescription_Len = 256
Private Const WSASYS_Status_Len = 128
Private Const WS_VERSION_REQD As Long = &H101
Private Const IP_SUCCESS As Long = 0
Private Const SOCKET_ERROR As Long = -1
Private Const AF_INET = 2

Private Type WSADATA
  wVersion As Integer
  wHighVersion As Integer
  szDescription(0 To WSADescription_Len) As Byte
  szSystemStatus(0 To WSASYS_Status_Len) As Byte
  imaxsockets As Integer
  imaxudp As Integer
  lpszvenderinfo As Long
End Type

Private Declare Function WSAStartup Lib "wsock32.dll" _
  (ByVal VersionReq As Long, _
   WSADataReturn As WSADATA) As Long
 
Private Declare Function WSACleanup Lib "wsock32.dll" () As Long

Private Declare Function inet_addr Lib "wsock32.dll" _
  (ByVal s As String) As Long

Private Declare Function gethostbyaddr Lib "wsock32.dll" _
  (haddr As Long, _
   ByVal hnlen As Long, _
   ByVal addrtype As Long) As Long

Private Declare Sub CopyMemory Lib "kernel32" _
   Alias "RtlMoveMemory" _
  (xDest As Any, _
   xSource As Any, _
   ByVal nbytes As Long)
   
Private Declare Function lstrlen Lib "kernel32" _
   Alias "lstrlenA" _
  (lpString As Any) As Long
 
 
Public Function SocketsInitialize() As Boolean

   Dim WSAD As WSADATA
   
   SocketsInitialize = WSAStartup(WS_VERSION_REQD, WSAD) = IP_SUCCESS
   
End Function


Public Sub SocketsCleanup()
   
   If WSACleanup() <> 0 Then
       MsgBox "Windows Sockets error occurred in Cleanup.", vbExclamation
   End If
   
End Sub


Public Function GetHostNameFromIP(ByVal sAddress As String) As String

   Dim ptrHosent As Long
   Dim hAddress As Long
   Dim nbytes As Long
   
   If SocketsInitialize() Then

     'convert string address to long
      hAddress = inet_addr(sAddress)
     
      If hAddress <> SOCKET_ERROR Then
         
        'obtain a pointer to the HOSTENT structure
        'that contains the name and address
        'corresponding to the given network address.
         ptrHosent = gethostbyaddr(hAddress, 4, AF_INET)
   
         If ptrHosent <> 0 Then
         
           'convert address and
           'get resolved hostname
            CopyMemory ptrHosent, ByVal ptrHosent, 4
            nbytes = lstrlen(ByVal ptrHosent)
         
            If nbytes > 0 Then
               sAddress = Space$(nbytes)
               CopyMemory ByVal sAddress, ByVal ptrHosent, nbytes
               GetHostNameFromIP = sAddress
            End If
         
         Else: MsgBox "Call to gethostbyaddr failed."
         End If 'If ptrHosent
     
      SocketsCleanup
     
      Else: MsgBox "String passed is an invalid IP."
      End If 'If hAddress
   
   Else: MsgBox "Sockets failed to initialize."
   End If  'If SocketsInitialize
     
End Function

'just called the function
GetHostNameFromIP("202.155.0.10")

   danny
   

0
Better Security Awareness With Threat Intelligence

See how one of the leading financial services organizations uses Recorded Future as part of a holistic threat intelligence program to promote security awareness and proactively and efficiently identify threats.

 

Author Comment

by:elchang
ID: 2809743
It works well, and would you answer me 3 questions additionally, Ark ?

1. Why do you change the parameter type from "const char FAR *" to "long" of addr in API gethostbyaddr?

2. Why do you create new structure T_host instead of using structure HOSTEN?

3. Can you recommand me some books on  Windows API for VB?


Thanks in advance!
EL
0
 
LVL 27

Expert Comment

by:Ark
ID: 2810107
Hi
1. char* FAR is pointer to address, which inet_addr function return, pointers are Long at 32 API
2. Anyway I have to create structure
(I can not call structures directly like in C - VB has not *.h files)
Type
.....
End type

I choose this name, but I could declare:

Type HOSTEN
    h_name As Long
    h_aliases As Long
    h_addrtype As Integer
    h_length As Integer
    h_addr_list As Long
End Type

3. The best books I know is Bruce McKinney "Hardcore Visual Basic" - you can find it on-line at microsoft site and Daniel Appleman "Visual Basic Programmer's Guide to the Win32 API". Also take a look at another book of last author

Cheers
0
 

Author Comment

by:elchang
ID: 2812622
Ark:

  I got it. Thanks for your guidance again.


Cheers
0

Featured Post

What Should I Do With This Threat Intelligence?

Are you wondering if you actually need threat intelligence? The answer is yes. We explain the basics for creating useful threat intelligence.

Join & Write a Comment

If you have ever used Microsoft Word then you know that it has a good spell checker and it may have occurred to you that the ability to check spelling might be a nice piece of functionality to add to certain applications of yours. Well the code that…
You can of course define an array to hold data that is of a particular type like an array of Strings to hold customer names or an array of Doubles to hold customer sales, but what do you do if you want to coordinate that data? This article describes…
As developers, we are not limited to the functions provided by the VBA language. In addition, we can call the functions that are part of the Windows operating system. These functions are part of the Windows API (Application Programming Interface). U…
Get people started with the process of using Access VBA to control Outlook using automation, Microsoft Access can control other applications. An example is the ability to programmatically talk to Microsoft Outlook. Using automation, an Access applic…

757 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

19 Experts available now in Live!

Get 1:1 Help Now