ping命令 仿源码实现 以及几个 命令的 使用

来源:互联网 发布:nosql数据库 编辑:程序博客网 时间:2024/05/23 16:26

ping localhost

ping 主机名

ping 主机IP

ping -a 主机IP

ping -t  主机IP

#include <iostream>#include <cstdio>#include <string>#include <WinSock2.h>#pragma comment(lib, "ws2_32.lib")//winsock库using namespace std;struct ICMPheader{    unsigned char    byType;    unsigned char    byCode;    unsigned short    nChecksum;    unsigned short    nId;    unsigned short    nSequence;};struct IPheader{    unsigned char    byVerLen;     unsigned char    byTos;     unsigned short    nTotalLength;     unsigned short    nId;     unsigned short    nOffset;     unsigned char    byTtl;     unsigned char    byProtocol;     unsigned short    nChecksum;     unsigned int    nSrcAddr;     unsigned int    nDestAddr; };unsigned short checkSum (char *pBuffer, int nLen){    unsigned short nWord;    unsigned int nSum = 0;    int i;    //Make 16 bit words out of every two adjacent 8 bit words in the packet    //and add them up    for (i = 0; i < nLen; i = i + 2)    {        nWord =((pBuffer [i] << 8)& 0xFF00) + (pBuffer [i + 1] & 0xFF);        nSum = nSum + (unsigned int)nWord;        }    //Take only 16 bits out of the 32 bit sum and add up the carries    while (nSum >> 16)    {        nSum = (nSum & 0xFFFF) + (nSum >> 16);    }    //One's complement the result    nSum = ~nSum;    return ((unsigned short) nSum);}int main(){    string str_dest_addr;    SOCKET sock_raw;    SOCKADDR_IN dest_addr;    SOCKADDR_IN from_addr;    char sendBuffer[1024] = {0};    char recvBuffer[1024] = {0};    WSADATA wsaData;    ::WSAStartup(MAKEWORD(2,2), &wsaData);    sock_raw = ::socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);    int timeout = 1000;    setsockopt(sock_raw, SOL_SOCKET, SO_RCVTIMEO, (char*)&timeout, sizeof(timeout));    setsockopt(sock_raw, SOL_SOCKET, SO_SNDTIMEO, (char*)&timeout, sizeof(timeout));    dest_addr.sin_family = AF_INET;    memset(&dest_addr.sin_zero, 0, 8);    while( cout << "ping>")    {        cin >> str_dest_addr;        int nSeq = 0;        int nPacketSent = 0;        int nPacketReceived = 0;        int nTotalRoundTime = 0;        int nMaxRoundTime = 0;        int nMinRoundTime = -1;        if((dest_addr.sin_addr.S_un.S_addr = inet_addr(str_dest_addr.c_str())) == INADDR_NONE)        {            struct hostent *hp = NULL;            if((hp = gethostbyname(str_dest_addr.c_str())) != NULL)            {                memcpy(&(dest_addr.sin_addr), hp->h_addr_list[0],hp->h_length);            }            else            {                cout << "can not find the host!" << endl;                continue;            }        }        while( nPacketSent < 4)        {            nPacketSent++;            ICMPheader* pIcmpHeader = (ICMPheader*)sendBuffer;            pIcmpHeader->byType = 8;            pIcmpHeader->byCode = 0;            pIcmpHeader->nId = (USHORT)::GetCurrentProcessId();            pIcmpHeader->nChecksum = 0;                    pIcmpHeader->nSequence = htons(nSeq++);            memset(sendBuffer + sizeof(ICMPheader), '*', 32);            pIcmpHeader->nChecksum = htons(checkSum(sendBuffer, sizeof(ICMPheader) + 32));                        int nRet = sendto(sock_raw, sendBuffer, sizeof(ICMPheader) + 32, 0, (SOCKADDR*)&dest_addr, sizeof(SOCKADDR_IN));            if(nRet == SOCKET_ERROR)            {                cout << "send error:" << ::WSAGetLastError() << endl;                break;            }            unsigned long dwSendTime = ::GetTickCount();            int fromLen = sizeof(SOCKADDR_IN);            nRet = recvfrom(sock_raw, recvBuffer, 1024, 0, (SOCKADDR*)&from_addr,&fromLen);            if(nRet == SOCKET_ERROR)            {                if(::WSAGetLastError() == WSAETIMEDOUT)                {                    cout << "Request time out" << endl;                    continue;                }                break;            }            IPheader* ipHdr = (IPheader*)recvBuffer;            ICMPheader* icmpHdrRet = (ICMPheader*)(recvBuffer + sizeof(IPheader));            if( icmpHdrRet->byCode == 0 &&                icmpHdrRet->nId == pIcmpHeader->nId &&                icmpHdrRet->nSequence == pIcmpHeader->nSequence)            {                nPacketReceived++;                unsigned long dwRecvTime = ::GetTickCount();                int nRoundTime = dwRecvTime - dwSendTime;                nTotalRoundTime += nRoundTime;                if(nMinRoundTime == -1)                {                    nMinRoundTime = nRoundTime;                    nMaxRoundTime = nRoundTime;                }                if( nRoundTime < nMinRoundTime)                {                    nMinRoundTime = nRoundTime;                }                                if( nRoundTime > nMaxRoundTime)                {                    nMaxRoundTime = nRoundTime;                }                            cout << "Reply from " << inet_ntoa(from_addr.sin_addr) << ": bytes = " << nRet - sizeof(ICMPheader) - sizeof(IPheader) << ", time = " << nRoundTime << "ms, TTL = " << (int)ipHdr->byTtl << endl;            }            else            {                cout << "The echo reply is not correct!" << endl;            }            Sleep(1000);        }        cout << endl << "Ping statistics for " << inet_ntoa(from_addr.sin_addr) << ":" << endl << "\t" << "Packets:sent = " << nPacketSent << ", Received = "            << nPacketReceived << ", Lost = " << (nPacketSent - nPacketReceived) << "(" << ((float)(nPacketSent - nPacketReceived) /nPacketSent) * 100 << "% loss)" << endl;        if(nPacketReceived)        {            cout << "\rApproximate round trip times in milli-seconds:" << endl << '\t' << "Minimum = " << nMinRoundTime <<             "ms, Maximum = " << nMaxRoundTime << "ms, Average = " << (float)nTotalRoundTime /nPacketReceived << "ms" << endl;        }    }    ::closesocket(sock_raw);    ::WSACleanup();    return 0;}



0 0
原创粉丝点击