사용자 도구

사이트 도구


kb:windowsiphelperapi

IP Helper API

IP Helper 함수들은 로컬 머신의 네트워크 설정을 검색 및 수정할 수 있도록 해주는 함수들이다. 또한 네트워크 설정이 변경된 경우, 이를 애플리케이션에게 통지해주는 기능도 제공한다.

핑 때리기

#include <IPExport.h>
#include <icmpapi.h>
 
hostent* host = NULL;
in_addr inaddr;
inaddr.s_addr = ::inet_addr("155.230.29.10");
if (inaddr.s_addr == INADDR_NONE)
{
    host = ::gethostbyname("155.230.29.10");
}
else 
{
    host = ::gethostbyaddr((const char*)&inaddr, sizeof(inaddr), AF_INET);
}
 
if (host != NULL)
{
    // ICMP 핸들을 생성한다. IPv6일 경우에는 Icmp6CreateFile()을 사용한다.
    HANDLE hICMP = ::IcmpCreateFile();
 
    ICMP_ECHO_REPLY iep;
    iep.RoundTripTime = 0xFFFFFFFF;
 
    DWORD dw = ::IcmpSendEcho(hICMP,
        *((ULONG*)host->h_addr_list[0]),
        0,0,NULL,
        &iep, sizeof(ICMP_ECHO_REPLY), 5000);
 
    cout << "RoundTripTime:" << iep.RoundTripTime << endl;
 
    ::IcmpCloseHandle(hICMP);
}

플랫폼 SDK를 다운로드받은 다음, include 패스 잡아주고, iphlpapi.lib를 링크해줘야한다. 하지만 이렇게 해도 iphlpapi.dll에 IcmpCloseHandle이 없다고 에러가 났다. 짱난다. MSDN에 봐도 뭔가 일관성이 없고 - 다른 함수들은 iphlpapi.lib를 링크하라고 되어있는데, IcmpCloseHandle은 icmp.lib를 링크하라고 되어있는데다가, 플랫폼 SDK에 이런 라이브러리가 없다. - 문제가 많은 듯 하다.

네트워크 카드에 대한 정보 알아내기

GetAdaptersInfo 함수를 이용해 랜 카드의 IP 주소, MAC 주소, 현재 게이트웨이 등을 알아낼 수 있다.

DWORD GetAdaptersInfo(
  PIP_ADAPTER_INFO pAdapterInfo,
  PULONG pOutBufLen
);
typedef struct _IP_ADAPTER_INFO 
{  
    struct _IP_ADAPTER_INFO* Next;  
    DWORD ComboIndex;  
    char AdapterName[MAX_ADAPTER_NAME_LENGTH + 4];  
    char Description[MAX_ADAPTER_DESCRIPTION_LENGTH + 4];  
    UINT AddressLength;  
    BYTE Address[MAX_ADAPTER_ADDRESS_LENGTH];  // MAC 주소
    DWORD Index;  
    UINT Type;  
    UINT DhcpEnabled;  
    PIP_ADDR_STRING CurrentIpAddress;
    IP_ADDR_STRING IpAddressList;       // IP 주소
    IP_ADDR_STRING GatewayList;  
    IP_ADDR_STRING DhcpServer;  
    BOOL HaveWins;  
    IP_ADDR_STRING PrimaryWinsServer;  
    IP_ADDR_STRING SecondaryWinsServer;  
    time_t LeaseObtained;  
    time_t LeaseExpires;
} IP_ADAPTER_INFO, *PIP_ADAPTER_INFO;

WMI의 Win32_NetworkAdapterConfiguration 클래스를 통해서도 비슷한 정보를 알아낼 수 있다. 참고로 IP만을 원하는 것이라면 다음과 같은 코드로도 알아낼 수 있다. 다만 루프백 주소(127.0.0.1)을 주의하기 바란다.

#include <iostream.h>
#include <winsock.h>
 
int main(int argc, char *argv[])
{
    WSAData wsaData;
    if (::WSAStartup(MAKEWORD(1, 1), &wsaData) != 0) 
        return 255;
 
    try
    {
        char ac[80] = {0,};
 
        if (gethostname(ac, sizeof(ac)) == SOCKET_ERROR) 
        {
            cerr << "Error " << WSAGetLastError() 
                << " when getting local host name." << endl;
            throw;
        }
 
        cout << "Host name is " << ac << "." << endl;
 
        struct hostent *phe = gethostbyname(ac);
        if (phe == 0) 
        {
            cerr << "Yow! Bad host lookup." << endl;
            throw;
        }
 
        for (int i=0; phe->h_addr_list[i] != 0; i++) 
        {
            struct in_addr addr;
            memcpy(&addr, phe->h_addr_list[i], sizeof(struct in_addr));
            cout << "Address " << i << ": " << inet_ntoa(addr) << endl;
        }
    }
    catch (...)
    {
        cerr << "Something bad happen!" << endl;
    }
 
    ::WSACleanup();
    return 0;
}

링크

kb/windowsiphelperapi.txt · 마지막으로 수정됨: 2014/11/09 21:31 (바깥 편집)