zoukankan      html  css  js  c++  java
  • TraceRoute(tracert)源码(基于ICMP.DLL实现)

      TraceRoute(tracert)源码(基于ICMP.DLL实现) 佟强 2008.11.4

    TraceRoute的实现原理 http://blog.csdn.net/microtong/archive/2008/11/04/3220450.aspx

        本程序直接使用ICMP.DLL动态链接库中的函数来发送ICMP回显请求报文,用以探测路由信息,输出每一跳路由器的IP和往返时间,实现tracert的功能。

    1. //TraceRoute3.cpp
    2. #include <stdio.h>
    3. #include <winsock2.h>
    4. #include <windows.h>
    5. #include <IPHlpApi.h>
    6. //增加静态链接库ws2_32.lib
    7. #pragma comment(lib,"ws2_32.lib")
    8. //声明3个函数类型的指针
    9. typedef HANDLE (WINAPI *lpIcmpCreateFile)(VOID);
    10. typedef BOOL (WINAPI *lpIcmpCloseHandle)(HANDLE  IcmpHandle);
    11. typedef DWORD (WINAPI *lpIcmpSendEcho)(
    12.     HANDLE                   IcmpHandle,
    13.     IPAddr                   DestinationAddress,
    14.     LPVOID                   RequestData,
    15.     WORD                     RequestSize,
    16.     PIP_OPTION_INFORMATION   RequestOptions,
    17.     LPVOID                   ReplyBuffer,
    18.     DWORD                    ReplySize,
    19.     DWORD                    Timeout
    20.     );
    21. int main(int argc,char* argv[]){
    22.  if(argc!=2){
    23.   printf("Usage: %s destIP/n",argv[0]);
    24.   exit(-1);
    25.  }
    26.  WSADATA wsa;
    27.  if(WSAStartup(MAKEWORD(2,2),&wsa)!=0){
    28.   printf("WSAStartup failed./n");
    29.   exit(-1);
    30.  }
    31.  //转换IP地址到整数
    32.  unsigned long ip = inet_addr(argv[1]);
    33.  if(ip==INADDR_NONE){
    34.   //用户可能输入的是域名
    35.   hostent* pHost = gethostbyname(argv[1]);
    36.   //如果域名无法解析
    37.   if(pHost==NULL){
    38.    printf("Invalid IP or domain name: %s/n", argv[1]);
    39.    exit(-1);
    40.   }
    41.   //取域名的第一个IP地址
    42.   ip = *(unsigned long*)pHost->h_addr_list[0];
    43.   printf("trace route to %s(%s)/n/n",argv[1],inet_ntoa(*(in_addr*)&ip));
    44.  }else{
    45.   printf("trace route to %s/n/n",argv[1]);
    46.  }
    47.  //载入ICMP.DLL动态库
    48.  HMODULE hIcmpDll = LoadLibrary("icmp.dll");
    49.  if(hIcmpDll==NULL){
    50.   printf("fail to load icmp.dll/n");
    51.   exit(-1);
    52.  }
    53.  //定义3个函数指针
    54.  lpIcmpCreateFile IcmpCreateFile;
    55.  lpIcmpCloseHandle IcmpCloseHandle;
    56.  lpIcmpSendEcho IcmpSendEcho;
    57.  //从ICMP.DLL中获取所需的函数入口地址
    58.  IcmpCreateFile = (lpIcmpCreateFile)GetProcAddress(hIcmpDll,"IcmpCreateFile");
    59.  IcmpCloseHandle = (lpIcmpCloseHandle)GetProcAddress(hIcmpDll,"IcmpCloseHandle");
    60.  IcmpSendEcho = (lpIcmpSendEcho)GetProcAddress(hIcmpDll,"IcmpSendEcho");
    61.  //打开ICMP句柄
    62.  HANDLE hIcmp;
    63.  if ((hIcmp = IcmpCreateFile()) == INVALID_HANDLE_VALUE){
    64.   printf("/tUnable to open ICMP file./n");
    65.   exit(-1);
    66.  }
    67.  //设置IP报头的TTL值
    68.  IP_OPTION_INFORMATION IpOption;
    69.  ZeroMemory(&IpOption,sizeof(IP_OPTION_INFORMATION));
    70.  IpOption.Ttl = 1;
    71.  //设置要发送的数据
    72.  char SendData[32];
    73.  memset(SendData,'0',sizeof(SendData));
    74.  //设置接收缓冲区
    75.  char ReplyBuffer[sizeof(ICMP_ECHO_REPLY)+32];
    76.  PICMP_ECHO_REPLY pEchoReply = (PICMP_ECHO_REPLY)ReplyBuffer;
    77.  BOOL bLoop = TRUE;
    78.  int iMaxHop = 30;
    79.  while(bLoop && iMaxHop--){
    80.   printf("%2d: ",IpOption.Ttl);
    81.   //发送ICMP回显请求
    82.   if(IcmpSendEcho(hIcmp,(IPAddr)ip, SendData, sizeof(SendData), &IpOption, 
    83.    ReplyBuffer, sizeof(ReplyBuffer), 3000)!=0){
    84.     if(pEchoReply->RoundTripTime==0){
    85.      printf("/t<1ms");
    86.     }else{
    87.      printf("/t%dms",pEchoReply->RoundTripTime);
    88.     }
    89.     printf("/t%s/n",inet_ntoa(*(in_addr*)&(pEchoReply->Address)));
    90.     //判断是否完成路由路径探测
    91.     if((unsigned long)pEchoReply->Address==ip){
    92.      printf("/nTrace complete./n");
    93.      bLoop = FALSE;
    94.     }
    95.   }else{
    96.    printf("/t*/tRequest time out./n");
    97.   }
    98.   IpOption.Ttl++;
    99.  }
    100.  IcmpCloseHandle(hIcmp);
    101.  FreeLibrary(hIcmpDll);
    102.  WSACleanup();
    103.  return 0;
    104. }
  • 相关阅读:
    find
    fdisk
    falcon-eye
    ethtools
    e2fsck
    dpkg
    declare
    df
    debconf-utils
    区块链从零开始做开发(0):hyperledger Fabric2.3安装
  • 原文地址:https://www.cnblogs.com/zhangyunlin/p/6168125.html
Copyright © 2011-2022 走看看