📄 ping.cpp
字号:
#include "stdafx.h"
#include "ThreadInfo.h"
u_short in_cksum(u_short *addr, int len)
{
register int nleft = len;
register u_short *w = addr;
register u_short answer;
register int sum = 0;
/*
* Our algorithm is simple, using a 32 bit accumulator (sum),
* we add sequential 16 bit words to it, and at the end, fold
* back all the carry bits from the top 16 bits into the lower
* 16 bits.
*/
while( nleft > 1 ) {
sum += *w++;
nleft -= 2;
}
/* mop up an odd byte, if necessary */
if( nleft == 1 ) {
u_short u = 0;
*(u_char *)(&u) = *(u_char *)w ;
sum += u;
}
/*
* add back carry outs from top 16 bits to low 16 bits
*/
sum = (sum >> 16) + (sum & 0xffff); /* add hi 16 to low 16 */
sum += (sum >> 16); /* add carry */
answer = ~sum; /* truncate to 16 bits */
return (answer);
}
int SendEchoRequest(SOCKET s, LPSOCKADDR_IN lpstToAddr)
{
static ECHOREQUEST echoReq;
static nId = 1;
static nSeq = 1;
int nRet;
// Fill in echo request
echoReq.icmpHdr.Type = ICMP_ECHOREQ;
echoReq.icmpHdr.Code = 0;
echoReq.icmpHdr.Checksum = 0;
echoReq.icmpHdr.ID = nId++;
echoReq.icmpHdr.Seq = nSeq++;
// Fill in some data to send
for (nRet = 0; nRet < REQ_DATASIZE; nRet++)
echoReq.cData[nRet] = ' '+nRet;
// Save tick count when sent
echoReq.dwTime = GetTickCount();
// Put data in packet and compute checksum
echoReq.icmpHdr.Checksum = in_cksum((u_short *)&echoReq, sizeof(ECHOREQUEST));
// Send the echo request
nRet = sendto(s, /* socket */
(LPSTR)&echoReq, /* buffer */
sizeof(ECHOREQUEST),
0, /* flags */
(LPSOCKADDR)lpstToAddr, /* destination */
sizeof(SOCKADDR_IN)); /* address length */
return (nRet);
}
int WaitForEchoReply(SOCKET s)
{
struct timeval Timeout;
fd_set readfds;
readfds.fd_count = 1;
readfds.fd_array[0] = s;
Timeout.tv_sec = 1;
Timeout.tv_usec = 0;
return(select(1, &readfds, NULL, NULL, &Timeout));
}
DWORD RecvEchoReply(SOCKET s, LPSOCKADDR_IN lpsaFrom, u_char *pTTL)
{
ECHOREPLY echoReply;
int nRet;
int nAddrLen = sizeof(struct sockaddr_in);
// Receive the echo reply
nRet = recvfrom(s, // socket
(LPSTR)&echoReply, // buffer
sizeof(ECHOREPLY), // size of buffer
0, // flags
(LPSOCKADDR)lpsaFrom, // From address
&nAddrLen); // pointer to address len
// Check return value
// return time sent and IP TTL
*pTTL = echoReply.ipHdr.TTL;
return(echoReply.echoRequest.dwTime);
}
UINT PingThread( LPVOID pParam )
{
CThreadInfo* pThreadInfo = (CThreadInfo*)pParam;
HWND m_hWnd = pThreadInfo->m_hwndNotifyWnd;
SOCKET rawSocket;
struct sockaddr_in saDest;
struct sockaddr_in saSrc;
LPHOSTENT lpHost;
CString str;
int nRet;
DWORD dwTimeSent,dwElapsed;
u_char cTTL;
long m_laddr;
rawSocket = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);
while (TRUE)
{
if (WaitForSingleObject(pThreadInfo->m_hEventStartPing,INFINITE)
!= WAIT_OBJECT_0)
break;
if (WaitForSingleObject(pThreadInfo->m_hEventKillPing,0)
== WAIT_OBJECT_0)
break;
str.Format("读取计算机:%s地址",pThreadInfo->strHost);
::SendMessage(m_hWnd,WM_MSG_STATUS,0,(LPARAM) LPCTSTR(str));
m_laddr = inet_addr(pThreadInfo->strHost);
if (m_laddr == INADDR_NONE)
{
lpHost = gethostbyname(pThreadInfo->strHost);
if (lpHost == NULL)
{
str.Format("计算机名字无效: %s", pThreadInfo->strHost);
::PostMessage(m_hWnd,WM_MSG_STATUS, 0, (LPARAM) LPCTSTR (str));
::PostMessage(m_hWnd,WM_MSG_PINGSTOP,0,0);
::PostMessage(m_hWnd,WM_MSG_STATUS, 0, (LPARAM) "完成!");
continue;
}
saDest.sin_addr.s_addr = *((u_long FAR *) (lpHost->h_addr));
}
else
{
saDest.sin_addr.s_addr =m_laddr;
}
saDest.sin_family = AF_INET;
saDest.sin_port = 0;
str.Format("Pinging %s [%s] with %d bytes of data:",
pThreadInfo->strHost,
inet_ntoa(saDest.sin_addr),
REQ_DATASIZE);
::PostMessage(m_hWnd,WM_MSG_STATUS, 0, (LPARAM) LPCTSTR (str));
if (WaitForSingleObject(pThreadInfo->m_hEventKillPing,0)
== WAIT_OBJECT_0)
break;
for (int nLoop = 0; nLoop < pThreadInfo->nRetries; nLoop++)
{
// Send ICMP echo request
if (WaitForSingleObject(pThreadInfo->m_hEventStopPing,0)
== WAIT_OBJECT_0)
break;
if (WaitForSingleObject(pThreadInfo->m_hEventKillPing,0)
== WAIT_OBJECT_0)
break;
SendEchoRequest(rawSocket, &saDest);
nRet = WaitForEchoReply(rawSocket);
if (!nRet)
{
str.Format("超时");
::PostMessage(m_hWnd,WM_MSG_STATUS, 0, (LPARAM) LPCTSTR (str));
}
else
{
// Receive reply
dwTimeSent = RecvEchoReply(rawSocket, &saSrc, &cTTL);
// Calculate elapsed time
dwElapsed = GetTickCount() - dwTimeSent;
str.Format("Reply[%d] from: %s: bytes=%d time=%ldms TTL=%d",
nLoop+1,
inet_ntoa(saSrc.sin_addr),
REQ_DATASIZE,
dwElapsed,
cTTL);
::PostMessage(m_hWnd,WM_MSG_STATUS, 0, (LPARAM) LPCTSTR (str));
}
}
::PostMessage(m_hWnd,WM_MSG_PINGSTOP,0,0);
::PostMessage(m_hWnd,WM_MSG_STATUS, 0, (LPARAM) "完成!");
if (WaitForSingleObject(pThreadInfo->m_hEventKillPing,0)
== WAIT_OBJECT_0)
break;
}
nRet = closesocket(rawSocket);
ResetEvent(pThreadInfo->m_hEventKillPing);
SetEvent(pThreadInfo->m_hEvenPingtKilled);
return 1;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -