#include <Winsock2.h>
#pragma comment(lib, "Ws2_32.lib")
#include <icmpapi.h>
#pragma comment(lib, "Iphlpapi.lib")
// Initialize Winsock
struct _tagWinSockInit_t
{
_tagWinSockInit_t()
{
WSADATA wsaData;
int iResult = WSAStartup(MAKEWORD(2, 2), &wsaData);
if( iResult != 0)
{
printf( "WSAStartup failed %u\n", iResult);
}
}
~_tagWinSockInit_t()
{
WSACleanup();
}
}m_SockInit;
class CIcmpBase
{
protected:
HANDLE m_hIcmp;
public:
CIcmpBase()
{
m_hIcmp = IcmpCreateFile();
if(m_hIcmp == INVALID_HANDLE_VALUE)
{
printf("IcmpCreateFile failed %u\n", GetLastError());
}
}
virtual ~CIcmpBase()
{
if(m_hIcmp != INVALID_HANDLE_VALUE)
{
IcmpCloseHandle(m_hIcmp);
m_hIcmp = INVALID_HANDLE_VALUE;
}
}
//解析目标地址
BOOL GetHostAddr(LPCSTR sHostName, IPAddr &dstIP)
{
BOOL bRet = FALSE;
struct hostent *remoteHost = gethostbyname(sHostName);
if(remoteHost)
{
dstIP = *(u_long *) remoteHost->h_addr_list[0];
bRet = TRUE;
}
else
{
printf("gethostbyname(%s) failed %u\n",
sHostName, WSAGetLastError());
}
return bRet;
}
};
class CIcmpPing : public CIcmpBase
{
public:
BOOL Ping(LPCSTR sHostName, DWORD dwTmOut=1000)
{
int iRet = 0;
IPAddr dstIP = 0;
char SendData[32] = {"Fill for test ICMP data"};
char chAckData[256] = {0};
ICMP_ECHO_REPLY *pEchoReply = (ICMP_ECHO_REPLY *)chAckData;
DWORD dwEcho;
in_addr inAddr;
if(m_hIcmp != INVALID_HANDLE_VALUE && GetHostAddr(sHostName, dstIP))
{
dwEcho = IcmpSendEcho(m_hIcmp, dstIP, &SendData, sizeof(SendData),
NULL, chAckData, sizeof(chAckData), dwTmOut);
if(dwEcho)
{
//输出一些信息
inAddr.s_addr = pEchoReply->Address;
printf("Reply from %s: bytes=%d TTL=%d\n",
inet_ntoa(inAddr), pEchoReply->DataSize,
pEchoReply->Options.Ttl);
iRet ++;
}
else
{
printf("IcmpSendEcho failed %u\n", GetLastError());
}
}
return iRet;
}
};
//测试用例
CIcmpPing icmp;
icmp.Ping("127.0.0.1");
icmp.Ping("www.sina.com.cn");
//测试输出
Reply from 127.0.0.1: bytes=32 TTL=64
Reply from 202.102.94.124: bytes=32 TTL=56 |