一个简单嗅探器的实现

这是最近的一段代码。

也没有什么好说的,简单的socket编程,设置网卡为混杂模式,接受所有封包,并打印所有封包的基本信息,及内容。

#include<stdio.h> #include<winsock2.h> #include<string.h> #include<windows.h> #include<mstcpip.h> #pragma comment(lib,"ws2_32.lib") #define RECVPORT 7000 //绑定的接包端口号 struct iphdr { unsigned char head; unsigned char tos; unsigned short length; //IP包头定义 unsigned short flags; unsigned short offset; unsigned char ttl; unsigned char protc; unsigned short checksum; unsigned int sourceip; unsigned int destip; }; struct udphdr { unsigned int sourceport; unsigned int destport; unsigned int length; //UDP包头定义 unsigned int checksum; }; struct tcphdr { USHORT sourceport; USHORT destport; unsigned int seq; unsigned int ack; //TCP包头定义 unsigned char offset; unsigned char flags; USHORT win; USHORT checksum; USHORT urg; }; FILE *f; char orig[100],*p,end; char type[20]={0},version[20]={0},plat[20]={0},ttl[20]={0},win[20]={0},df[20]={0},tos[20]={0}; int i=0,j=0; int ttli,dfi,tosi,winb,wine; bool winf=false; int solve(char *buff) //解包函数定义 { struct iphdr *ip; struct tcphdr *tcp; struct udphdr *udp; struct sockaddr_in test1,test2; BYTE *datat=NULL,*datau=NULL; BYTE test; ip=(struct iphdr*)buff; //取IP头 tcp=(struct tcphdr*)(buff+((ip->head)&0xf)*sizeof(unsigned int)); //取TCP头 udp=(struct udphdr*)(buff+((ip->head)&0xf)*sizeof(unsigned int)); //取UDP头 test1.sin_addr.s_addr=ip->sourceip; test2.sin_addr.s_addr=ip->destip; datat=((BYTE *)tcp)+(tcp->offset>>4)*4; datau=(BYTE *)udp; printf("从:%s,",inet_ntoa(test1.sin_addr)); printf("到:%s\n",inet_ntoa(test2.sin_addr)); switch(ip->protc) { case 1:printf("Proto ICMP,");break; case 2:printf("Proto IGMP,");break; case 6:printf("Proto TCP,");break; case 8:printf("Proto EGP,");break; case 9:printf("Proto IGP,");break; case 17:printf("Proto UDP,");break; case 41:printf("Proto IPv6,");break; case 89:printf("Proto OSPF,");break; default:printf("Proto error,");break; } if(ip->protc==6) { int port=0; port=ntohs(tcp->sourceport); printf("从TCP端口:%d,到TCP端口:%d,SEQ:%d,ACK:%d\n",ntohs(tcp->sourceport),ntohs(tcp->destport),ntohl(tcp->seq),ntohl(tcp->ack)); switch(port) { case 21:printf("这是一个ftp协议数据包\n");break; case 80:printf("这是一个HTTP协议数据包\n");break; case 110:printf("这是一个pop3协议数据包\n");break; case 25:printf("这是一个SMTP协议数据包\n ");break; } printf("FLAGS:"); if(tcp->flags&0x20) printf("URG "); if(tcp->flags&0x10) printf("ACK "); if(tcp->flags&0x8) //对TCP命令,输出标志位 printf("PSH "); if(tcp->flags&0x4) printf("RST "); if(tcp->flags&0x2) printf("SYN "); if(tcp->flags&0x1) printf("FIN "); printf("data:%s\n",datat); } else if(ip->protc==17) { printf("从UDP端口:%d,到UDP端口:%d,\nDATA:%s",ntohs(udp->sourceport),ntohs(udp->destport),datau); } printf("TTL:%d\n",ip->ttl); printf("\n"); return 0; } int main() { WSADATA ws; long lresult; SOCKET sock; struct sockaddr_in myaddress; //定义主函数变量 struct hostent *host; char name[100],buffer[65535],k; int err1,err2,err3,i; printf("输入ENTER键开始\n"); k=getchar(); lresult=WSAStartup(MAKEWORD(2,2),&ws); if(lresult<0) printf("error!"); myaddress.sin_family=AF_INET; myaddress.sin_port=htons(RECVPORT); //初始化 gethostname(name,sizeof(name)); host=gethostbyname(name); memcpy(&myaddress.sin_addr,host->h_addr_list[0],host->h_length); sock=socket(AF_INET,SOCK_RAW,IPPROTO_IP); err2=bind(sock,(PSOCKADDR)&myaddress,sizeof(myaddress)); //绑定端口 if(err2<0) { printf("BIND ERROR!"); exit(1); } DWORD inbuffer=1; DWORD outbuffer[10]; DWORD returned=0; err1=WSAIoctl(sock,SIO_RCVALL,&inbuffer,sizeof(inbuffer),&outbuffer,sizeof(outbuffer),&returned,NULL,NULL); if(err1<0) { printf("IO OPTION SET ERROR!"); //设置端口为接收所有包模式 exit(1); } for(i=1;i<=30;i++) { memset(buffer,0,sizeof(buffer));//清空接收缓冲区 err3=recv(sock,buffer,sizeof(buffer),0); //接包 if(err3<0) { printf("RECEIVE ERROR!"); exit(1); } solve(buffer); //定义解包函数解包 } return 0; }

一个简单嗅探器的实现
菜鸟言论,仅供娱乐。