发新话题
打印

[转载]免费Sniffer工具Guniffer的代码

[转载]免费Sniffer工具Guniffer的代码

文章作者:Shotgun

Guniffer.CPP
复制内容到剪贴板
代码:
//////////////////////////////////////////////////////////////////////////
//                                                                        //               
//    GUNiffer   For Win2K by Shotgun                                    //
//                                                                        //
//    Version:    0.30 Beta                                                //
//    Released:    [2001.4]                                               //
//    Author:        [Shotgun]                                               //
//    Homepage:                                                           //
//                [[url]http://IT.Xici.Net[/url]]                                   //
//                [[url]http://www.Patching.Net[/url]]                               //
//                                                                       //
//////////////////////////////////////////////////////////////////////////
#include <math.h>
#include <stdio.h>
#include <string.h>
#include <Winsock2.h>
#include <mstcpip.h>

#define STATUS_FAILED 0xFFFF        //定义异常出错代码
#define MAX_PACK_LEN  65535            //接收的最大IP报文   
#define MAX_ADDR_LEN  16            //点分十进制地址的最大长度
#define MAX_PROTO_TEXT_LEN    16        //子协议名称(如"TCP")最大长度
#define MAX_PROTO_NUM 12            //子协议数量
#define MAX_HOSTNAME_LAN 255        //最大主机名长度
#define CMD_PARAM_HELP true

typedef struct _iphdr
{
    unsigned char    h_lenver;        //4位首部长度+4位IP版本号
    unsigned char    tos;            //8位服务类型TOS
    unsigned short    total_len;        //16位总长度(字节)
    unsigned short    ident;            //16位标识
    unsigned short    frag_and_flags;    //3位标志位
    unsigned char    ttl;            //8位生存时间 TTL
    unsigned char    proto;            //8位协议 (TCP, UDP 或其他)
    unsigned short    checksum;        //16位IP首部校验和
    unsigned int    sourceIP;        //32位源IP地址
    unsigned int    destIP;            //32位目的IP地址
}IP_HEADER;

typedef struct _tcphdr                //定义TCP首部
{
    USHORT th_sport;                //16位源端口
    USHORT th_dport;                //16位目的端口
    unsigned int  th_seq;            //32位序列号
    unsigned int  th_ack;            //32位确认号
    unsigned char th_lenres;        //4位首部长度/6位保留字
    unsigned char th_flag;            //6位标志位
    USHORT th_win;                    //16位窗口大小
    USHORT th_sum;                    //16位校验和
    USHORT th_urp;                    //16位紧急数据偏移量
}TCP_HEADER;

typedef struct _udphdr                //定义UDP首部
{
   unsigned short uh_sport;        //16位源端口
   unsigned short uh_dport;        //16位目的端口
   unsigned short uh_len;            //16位长度
   unsigned short uh_sum;            //16位校验和
} UDP_HEADER;

typedef struct _icmphdr                //定义ICMP首部
{
    BYTE  i_type;                    //8位类型
    BYTE  i_code;                    //8位代码
    USHORT i_cksum;                    //16位校验和
    USHORT i_id;                    //识别号(一般用进程号作为识别号)
    USHORT i_seq;                    //报文序列号   
    ULONG  timestamp;                //时间戳
}ICMP_HEADER;

typedef struct _protomap            //定义子协议映射表
{
    int  ProtoNum;
    char ProtoText[MAX_PROTO_TEXT_LEN];
}PROTOMAP;

PROTOMAP ProtoMap[MAX_PROTO_NUM]={    //为子协议映射表赋值
        { IPPROTO_IP  , "IP  " },
        { IPPROTO_ICMP , "ICMP" },  
        { IPPROTO_IGMP , "IGMP" },
        { IPPROTO_GGP  , "GGP " },  
        { IPPROTO_TCP  , "TCP " },  
        { IPPROTO_PUP  , "PUP " },  
        { IPPROTO_UDP  , "UDP " },  
        { IPPROTO_IDP  , "IDP " },  
        { IPPROTO_ND  , "NP  " },  
        { IPPROTO_RAW  , "RAW " },  
        { IPPROTO_MAX  , "MAX " },
        { NULL , ""    } };

SOCKET SockRaw;
char TcpFlag[6]={&#39;F&#39;,&#39;S&#39;,&#39;R&#39;,&#39;P&#39;,&#39;A&#39;,&#39;U&#39;};    //定义TCP标志位
bool ParamTcp    =false;                // -t关注TCP 报文
bool ParamUdp    =false;                // -u关注UDP 报文   
bool ParamIcmp    =false;                // -i关注ICMP报文
bool ParamDecode=false;                // -d对协议进行解码
char *strFromIpFilter=NULL;            // 源IP地址过滤
char *strDestIpFilter=NULL;            // 目的地址过滤
char *strSensitive=NULL;            // 敏感字符串
int  iPortFilter=0;                    // 端口过滤
int iProtocol, iTTL;               
char szProtocol[MAX_PROTO_TEXT_LEN];
char szSourceIP[MAX_ADDR_LEN], szDestIP[MAX_ADDR_LEN];

int DecodeIpPack(char *, int);        //IP解包函数
int DecodeTcpPack(char *, int);        //TCP解包函数
int DecodeUdpPack(char *, int);        //UDP解包函数
int DecodeIcmpPack(char *, int);    //ICMP解包函数
void CheckSockError(int, char*);    //出错处理函数
char * CheckProtocol(int);            //协议检查
void usage(void);                    //使用说明
bool GetCmdLine(int, char **);        //命令行参数处理

void main(int argc, char ** argv)
{
    int iErrorCode;
    char RecvBuf[MAX_PACK_LEN] = {0};
    usage();
    if(GetCmdLine(argc, argv)==CMD_PARAM_HELP) exit(0);
    //初始化SOCKET
    WSADATA wsaData;
    iErrorCode = WSAStartup(MAKEWORD(2,1),&wsaData);
    CheckSockError(iErrorCode, "WSAStartup");
    SockRaw = socket(AF_INET , SOCK_RAW , IPPROTO_IP);
    CheckSockError(SockRaw, "socket");
    //获取本机IP地址
    char FAR name[MAX_HOSTNAME_LAN];
    iErrorCode = gethostname(name, MAX_HOSTNAME_LAN);
    CheckSockError(iErrorCode, "gethostname");
    struct hostent FAR * pHostent;
    pHostent = (struct hostent * )malloc(sizeof(struct hostent));
    pHostent = gethostbyname(name);
    SOCKADDR_IN sa;
    sa.sin_family = AF_INET;
     sa.sin_port = htons(6000);
    memcpy(&sa.sin_addr.S_un.S_addr, pHostent->h_addr_list[0], pHostent->h_length);
    free(pHostent);
    iErrorCode = bind(SockRaw, (PSOCKADDR)&sa, sizeof(sa));
    CheckSockError(iErrorCode, "bind");
    //设置SOCK_RAW为SIO_RCVALL,以便接收所有的IP包
    DWORD dwBufferLen[10] ;
    DWORD dwBufferInLen = 1 ;
    DWORD dwBytesReturned = 0 ;
    iErrorCode=WSAIoctl(SockRaw, SIO_RCVALL,&dwBufferInLen, sizeof(dwBufferInLen),         
                &dwBufferLen, sizeof(dwBufferLen),&dwBytesReturned , NULL , NULL );
    CheckSockError(iErrorCode, "Ioctl");
    //侦听IP报文
    while(1)
    {
        memset(RecvBuf, 0, sizeof(RecvBuf));
        iErrorCode = recv(SockRaw, RecvBuf, sizeof(RecvBuf), 0);
        CheckSockError(iErrorCode, "recv");
        iErrorCode = DecodeIpPack(RecvBuf, iErrorCode);
        CheckSockError(iErrorCode, "Decode");
    }
}

//IP解包程序
int DecodeIpPack(char *buf, int iBufSize)
{
    IP_HEADER *pIpheader;
    SOCKADDR_IN saSource, saDest;
    pIpheader = (IP_HEADER *)buf;
//协议甄别
    iProtocol = pIpheader->proto;
    strncpy(szProtocol, CheckProtocol(iProtocol), MAX_PROTO_TEXT_LEN);
    if((iProtocol==IPPROTO_TCP) && (!ParamTcp)) return true;
    if((iProtocol==IPPROTO_UDP) && (!ParamUdp)) return true;
    if((iProtocol==IPPROTO_ICMP) && (!ParamIcmp)) return true;
//源地址
    saSource.sin_addr.s_addr = pIpheader->sourceIP;
    strncpy(szSourceIP, inet_ntoa(saSource.sin_addr), MAX_ADDR_LEN);
    if (strFromIpFilter)
        if (strcmp(strFromIpFilter,szSourceIP)) return true;
//目的地址
    saDest.sin_addr.s_addr = pIpheader->destIP;
    strncpy(szDestIP, inet_ntoa(saDest.sin_addr), MAX_ADDR_LEN);
    if (strDestIpFilter)
        if (strcmp(strDestIpFilter,szDestIP)) return true;
    iTTL = pIpheader->ttl;
//计算IP首部的长度
    int iIphLen = sizeof(unsigned long) * (pIpheader->h_lenver & 0xf);
//根据协议类型分别调用相应的函数
    switch(iProtocol)
    {
        case IPPROTO_TCP    :DecodeTcpPack(buf+iIphLen, iBufSize);break;
        case IPPROTO_UDP    :DecodeUdpPack(buf+iIphLen, iBufSize);break;
        case IPPROTO_ICMP    :DecodeIcmpPack(buf+iIphLen, iBufSize);break;
        default                :break;
    }
    //printf("\n");
    return true;
}

//协议识别程序
char * CheckProtocol(int iProtocol)
{
    for(int i=0; i<MAX_PROTO_NUM; i++)
            if(ProtoMap[i].ProtoNum==iProtocol)
                return ProtoMap[i].ProtoText;
    return "";
}

//TCP解包程序
int DecodeTcpPack(char * TcpBuf, int iBufSize)
{
    TCP_HEADER * pTcpHeader;
    int i;
    int iSourcePort,iDestPort;
   
    pTcpHeader = (TCP_HEADER * )TcpBuf;
    //计算TCP首部长度
    int TcpHeaderLen =  pTcpHeader->th_lenres>>4;
    TcpHeaderLen *= sizeof(unsigned long);
    char * TcpData=TcpBuf+TcpHeaderLen;
    //如果过滤敏感字符串则判断是否包含
    if (strSensitive)
        if ((strstr(TcpData, strSensitive))==NULL) return true;
    //对端口进行过滤
    iSourcePort = ntohs(pTcpHeader->th_sport);
    iDestPort = ntohs(pTcpHeader->th_dport);
    if ((iPortFilter) && (iSourcePort!=iPortFilter) && (iDestPort!=iPortFilter))
        return true;
    //输出
    printf("%s ", szProtocol);
    printf("%15s:%5d ->%15s:%5d  ", szSourceIP, iSourcePort, szDestIP, iDestPort);
    printf("TTL=%3d  ", iTTL);
    //判断TCP标志位
    unsigned char FlagMask = 1;
    for( i=0; i<6; i++ )
    {
        if((pTcpHeader->th_flag) & FlagMask) printf("%c",TcpFlag[i]);
        else printf("-");
        FlagMask=FlagMask<<1;
    }
    printf("  bytes=%4d", iBufSize);
    printf("\n");
    //对于长度大于40字节的包进行数据分析(IP_HEADER+TCP_HEADER=40)
    if ((ParamDecode) && (iBufSize>40))
    {
        //分析TCP数据段
        if ((!strSensitive) || (strstr(TcpData,strSensitive)))
        {
            printf(" [DATA]\n");
            printf("%s",TcpData);
            printf("\n [DATA END]\n\n\n");
        }
    }
    return true;
}

//UDP解包程序
int DecodeUdpPack(char * UdpBuf, int iBufSize)
{
    UDP_HEADER *pUdpHeader;
    pUdpHeader = (UDP_HEADER * )UdpBuf;
    int iSourcePort = ntohs(pUdpHeader->uh_sport);
    int iDestPort = ntohs(pUdpHeader->uh_dport);
    //对端口进行过滤
    if(iPortFilter)
        if ((iSourcePort!=iPortFilter) && (iDestPort!=iPortFilter))
            return true;
    printf("%s ", szProtocol);
    printf("%15s:%5d ->%15s:%5d  ", szSourceIP, iSourcePort, szDestIP, iDestPort);
    printf("TTL=%3d ", iTTL);
    printf("Len=%4d ", ntohs(pUdpHeader->uh_len));
    printf("bytes=%4d", iBufSize);
    printf("\n");
    //对于长度大于28字节的包进行数据分析(IP_HEADER+UDP_HEADER>28)
    if ((ParamDecode) && (iBufSize>28))
    {
        printf(" [DATA]\n");
        //UDP首部长度为8
        char * UdpData=UdpBuf+8;
        //分析UDP数据段
        for(unsigned int i=0;i<(iBufSize-sizeof(UDP_HEADER));i++)
        {
            if (!(i%8)) printf("\n");
            if ( (UdpData[i]>33) && (UdpData[i]<122) )
                    printf("%3c [%3x]", UdpData[i], UdpData[i]);
            else printf("   [%3x]", abs(UdpData[i]));
        }
        printf("\n [DATA END]\n\n\n");
    }
    return true;
}

//ICMP解包程序
int DecodeIcmpPack(char * IcmpBuf, int iBufSize)
{
    ICMP_HEADER * pIcmpHeader;
    pIcmpHeader = (ICMP_HEADER * )IcmpBuf;
    int iIcmpType = pIcmpHeader->i_type;
    int iIcmpCode = pIcmpHeader->i_code;
    //对类型进行过滤
    if ((iPortFilter) && (iIcmpType!=iPortFilter)) return true;
    printf("%s ", szProtocol);
    //printf("%15s Type%d ->%15s Code%d  ", szSourceIP, iIcmpType, szDestIP, iIcmpCode);
    printf("%15s     ->%15s      ", szSourceIP, szDestIP);
    printf("TTL=%3d ", iTTL);
    printf("Type%2d,%d ",iIcmpType,iIcmpCode);
    printf("bytes=%4d", iBufSize);
    printf("\n");
    //对于包含数据段的包进行数据分析
    if ((ParamDecode) && (iBufSize>28))
    {
        char * IcmpData=IcmpBuf+4;
        //分析ICMP数据段
        printf(" [DATA]");
        for(unsigned int i=0;i<(iBufSize-sizeof(ICMP_HEADER));i++)
        {
            if (!(i%8)) printf("\n");
            if ( (IcmpData[i]>33) && (IcmpData[i]<122) )
                    printf("%3c [%3x]", IcmpData[i], IcmpData[i]);
            else printf("   [%3x]", abs(IcmpData[i]));
        }
        printf("\n [DATA END]\n\n\n");
    }
    return true;
}

//命令行参数处理
bool GetCmdLine(int argc, char ** argv)
{
    if (argc<2) return CMD_PARAM_HELP;
    for(int i=1;i<argc;i++)
    {
        if(argv[i][0]!=&#39;/&#39;) return CMD_PARAM_HELP;
        else switch (argv[i][1])
            {
                case &#39;t&#39;:
                case &#39;T&#39;: ParamTcp=true; break;
                case &#39;u&#39;:
                case &#39;U&#39;: ParamUdp=true; break;
                case &#39;i&#39;:
                case &#39;I&#39;: ParamIcmp=true; break;
                case &#39;p&#39;:
                case &#39;P&#39;: ParamDecode=true; break;
                case &#39;f&#39;:
                case &#39;F&#39;:
                    {
                        strFromIpFilter=(char*)malloc(16*sizeof(char));
                        memset(strFromIpFilter,0,16*sizeof(char));
                        strcpy(strFromIpFilter,argv[i]+3);
                        break;
                    }
                case &#39;d&#39;:
                case &#39;D&#39;:
                    {
                        strDestIpFilter=(char*)malloc(16*sizeof(char));
                        memset(strDestIpFilter,0,16*sizeof(char));
                        strcpy(strDestIpFilter,argv[i]+3);
                        break;
                    }
                case &#39;s&#39;:
                case &#39;S&#39;:
                    {
                        strSensitive=(char*)malloc(255*sizeof(char));
                        memset(strSensitive,0,255*sizeof(char));
                        strcpy(strSensitive,argv[i]+3);
                        break;
                    }
                case &#39;o&#39;:
                case &#39;O&#39;:
                    {
                        iPortFilter=atoi(argv[i]+3);
                        break;
                    }
            }
    }
    printf("\nWill Sniffer");
    if(ParamTcp) printf(" TCP");
    if(ParamUdp) printf(" UDP");
    if(ParamIcmp) printf(" ICMP");
    if(strFromIpFilter) printf(" FromIp:%s",strFromIpFilter);
    if(strDestIpFilter) printf(" DestIp:%s",strDestIpFilter);
    if(ParamDecode) printf(" DECODE ON");
    if(strSensitive) printf(" Sensitive String:&#39;%s&#39;",strSensitive);
    printf("\n\tCTRL+C to quit\nStart:\n");
    return (!CMD_PARAM_HELP);
}

//使用说明
void usage(void)
{
    printf("GUNiffer\n");
    printf("\tSinffer for Win2K By Shotgun (Ver 0.3)\n");
    printf("\[email]tShotgun@Xici.net[/email]\n");
    printf("\thttp://It.Xici.Net\n");
    printf("\thttp://www.Patching.Net\n\n");
    printf("USAGE:\n");
    printf("\t/t       Output TCP  Packets\n");
    printf("\t/u       Output UDP  Packets\n");
    printf("\t/i       Output ICMP Packets\n");
    printf("\t/p       Decode Packets (default OFF)\n");
    printf("\t/f: fromIP  Output Packets FromIp=fromIP (default ALL)\n");
    printf("\t/d: destIP  Output Packets DestIp=destIP (default ALL)\n");
    printf("\t/s: string  Output Packets Include sensitive String(TCP only)\n");
    printf("\t/o: port   Output Packets from or to the port(ICMP is TYPE)\n");
    printf("Example:\n");
    printf("\tGUNiffer.exe /d>GUNiffer.log\n");
    printf("\tGUNiffer.exe /t /u /f:192.168.15.231\n");
    printf("\tGUNiffer.exe /t /p /s:PASS\n");
}

//SOCK错误处理程序
void CheckSockError(int iErrorCode, char *pErrorMsg)
{
    if(iErrorCode==SOCKET_ERROR)
    {
        printf("%s Error:%d\n", pErrorMsg, GetLastError());
        closesocket(SockRaw);
        exit(0);
    }
     
}
mstcpip.h
复制内容到剪贴板
代码:
//  Copyright (C) Microsoft Corporation, 1996-1999
#if _MSC_VER > 1000
#pragma once
#endif

/* Argument structure for SIO_KEEPALIVE_VALS */

struct tcp_keepalive {
   u_long  onoff;
   u_long  keepalivetime;
   u_long  keepaliveinterval;
};

// New WSAIoctl Options

#define SIO_RCVALL        _WSAIOW(IOC_VENDOR,1)
#define SIO_RCVALL_MCAST    _WSAIOW(IOC_VENDOR,2)
#define SIO_RCVALL_IGMPMCAST  _WSAIOW(IOC_VENDOR,3)
#define SIO_KEEPALIVE_VALS   _WSAIOW(IOC_VENDOR,4)
#define SIO_ABSORB_RTRALERT  _WSAIOW(IOC_VENDOR,5)
#define SIO_UCAST_IF       _WSAIOW(IOC_VENDOR,6)
#define SIO_LIMIT_BROADCASTS  _WSAIOW(IOC_VENDOR,7)
#define SIO_INDEX_BIND      _WSAIOW(IOC_VENDOR,8)
#define SIO_INDEX_MCASTIF    _WSAIOW(IOC_VENDOR,9)
#define SIO_INDEX_ADD_MCAST  _WSAIOW(IOC_VENDOR,10)
#define SIO_INDEX_DEL_MCAST  _WSAIOW(IOC_VENDOR,11)
qq310926是我唯一用号,除此之外有其他号码号自称邪八冰血封情,则非本人。

TOP

发新话题