《原始套接字编程》课程设计报告

整理文档很辛苦,赏杯茶钱您下走!

免费阅读已结束,点击下载阅读编辑剩下 ...

阅读已结束,您可以下载文档离线阅读编辑

资源描述

《原始套接字编程》课程设计报告姓名:王延兴班级:9班学号:541109041《原始套接字编程》课程设计报告班级:11级9班学号:54110904姓名:王延兴一、设计任务分析(一)实验环境操作系统:Windows编程工具及集成开发环境:VC++(二)实验目的和要求实验目的:掌握原始套接字编程。实验要求:完成下列功能:(1)利用RAWSOCKET捕获网络数据包的程序模型SOCKET_STREAM流式套接字SOCKET_DGRAMSOCKET_RAW原始套接字IPPROTO_IPIP协议IPPROTO_ICMPINTERNET控制消息协议,配合原始套接字可以实现ping的功能IPPROTO_IGMPINTERNET网关服务协议,在多播中用到在AF_INET地址族下,有SOCK_STREAM、SOCK_DGRAM、SOCK_RAW三种套接字类型。SOCK_STREAM也就是通常所说的TCP,而SOCK_DGRAM则是通常所说的UDP,而SOCK_RAW则是用于提供一些较低级的控制的;第3个参数依赖于第2个参数,用于指定套接字所用的特定协议,设为0表示使用默认的协议。RAWSOCKET能够对较低层次的协议直接访问,网络监听技术很大程度上依赖于它。(2)能够抓取第二节课的并发服务器程序的服务器端或客户端的应用层数据,即:时间值,打印输出。二、设计方案同一台主机不同进程可以用进程号来唯一标识,但是在网络环境下进程号并不能唯一标2识该进程。TCP/IP主要引入了网络地址、端口和连接等概念来解决网络间进程标识问题。套接字(Socket)是一个指向传输提供者的句柄,TCP/IP协议支持3种类型的套接字,分别是流式套接字、数据报式套接字和原始套接字。流式套接字(SOCKET_STREAM)提供了面向连接、双向可靠的数据流传输服务。数据报式套接字(SOCKET_DGRAM)提供了无连接服务,不提供无错保证。原始套接字(SOCKET_RAW)允许对较低层次的协议直接访问,比如IP、ICMP协议,它常用于检验新的协议实现,或者访问现有服务中配置的新设备,因为RAWSOCKET可以自如地控制Windows下的多种协议,能够对网络底层的传输机制进行控制,所以可以应用原始套接字来操纵网络层和传输层应用。比如,我们可以通过RAWSOCKET来接收发向本机的ICMP、IGMP协议包,或者接收TCP/IP栈不能够处理的IP包,也可以用来发送一些自定包头或自定协议的IP包。网络监听技术很大程度上依赖于SOCKET_RAW。本实验采用原始套接字进行捕获通过本主机的包并对本主机的包进行处理。各个函数功能:char*GetProtocol(intproto)//获得协议类型send(CientSocket,tmp,(int)strlen(tmp),0);发送数据recv(CientSocket,RecvBuffer,MAX_PATH,0);接收数据WSAStartup(MAKEWORD(2,2),&Ws)初始化套接字类库socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);创建套接字bind(ServerSocket,(structsockaddr*)&LocalAddr,sizeof(LocalAddr));绑定套接字listen(ServerSocket,10);侦听,队列大小为10设计思想:采用原始套接字进行捕获通过本主机的包并对本主机的包进行处理。三、详细设计头文件ip.h:详细代码://定义标准的的TCP头和IP头#defineURG0x20#defineACK0x10#definePSH0x08#defineRST0x04#defineSYN0x02#defineFIN0x01typedefstruct_iphdr//定义IP首部3{unsignedcharh_verlen;//4位首部长度+4位IP版本号unsignedchartos;//8位服务类型TOSunsignedshorttotal_len;//16位总长度(字节)unsignedshortident;//16位标识unsignedshortfrag_and_flags;//3位标志位unsignedcharttl;//8位生存时间TTLunsignedcharproto;//8位协议(TCP,UDP或其他)unsignedshortchecksum;//16位IP首部校验和unsignedintsourceIP;//32位源IP地址unsignedintdestIP;//32位目的IP地址}IP_HEADER;typedefstruct_tcphdr//定义TCP首部{USHORTth_sport;//16位源端口USHORTth_dport;//16位目的端口unsignedintth_seq;//32位序列号unsignedintth_ack;//32位确认号unsignedcharth_lenres;//4位首部长度/6位保留字unsignedcharth_flag;//6位标志位USHORTth_win;//16位窗口大小USHORTth_sum;//16位校验和USHORTth_urp;//16位紧急数据偏移量}TCP_HEADER;//定义ICMP首部typedefstructicmp_hdr{unsignedchari_type;//类型unsignedchari_code;//代码unsignedshorti_cksum;//校验码unsignedshorti_id;//非标准的ICMP首部unsignedshorti_seq;unsignedlongtimestamp;}ICMP_HEADER;typedefstructudp_hdr//8Bytes定义udp首部{unsignedshortuh_sport;unsignedshortuh_dport;4unsignedshortuh_len;unsignedshortuh_sum;}UDP_HEADER;源文件:详细代码:#includestdio.h#includeWinsock2.h#pragmacomment(lib,ws2_32)#defineSIO_RCVALL_WSAIOW(IOC_VENDOR,1)structip//定义IP首部{unsignedcharh_verlen;//4位首部长度,4位IP版本号unsignedchartos;//8位服务类型TOSunsignedshortip_length;//16位总长度(字节)unsignedshortident;//16位标识unsignedshortfrag_and_flags;//3位标志位unsignedcharttl;//8位生存时间TTLunsignedcharproto;//8位协议(TCP,UDP或其他)unsignedshortchecksum;//16位IP首部校验和unsignedintsourceIP;//32位源IP地址unsignedintdestIP;//32位目的IP地址};//定义TCP首部structtcp{USHORTth_sport;//16位源端口USHORTth_dport;//16位目的端口unsignedintth_seq;//32位序列号unsignedintth_ack;//32位确认号unsignedcharth_lenres;//4位首部长度/6位保留字unsignedcharth_flag;//6位标志位USHORTth_win;//16位窗口大小USHORTth_sum;//16位校验和USHORTth_urp;//16位紧急数据偏移量};voidmain(){intsock,bytes_recieved,fromlen;charbuffer[65535];structsockaddr_infrom;5structip*ip;structtcp*tcp;WORDwVersionRequested;//版本号WSADATAwsaData;//启动SOCKET的interr;wVersionRequested=MAKEWORD(2,2);//建立版本err=WSAStartup(wVersionRequested,&wsaData);//启用socketif(err!=0)//如果返回值不等于0,那么表示出错,直截退出程序{return;}sock=socket(AF_INET,SOCK_RAW,IPPROTO_IP);boolflag=true;setsockopt(sock,IPPROTO_IP,2,(char*)&flag,sizeof(flag));sockaddr_inaddr;addr.sin_family=AF_INET;addr.sin_addr.S_un.S_addr=inet_addr(127.0.0.1);//IP设置addr.sin_port=htons(0);if(SOCKET_ERROR==bind(sock,(sockaddr*)&addr,sizeof(addr)))//绑定{closesocket(sock);printf(绑定失败!);exit(0);}DWORDdwBytesRet;DWORDdwVal=1;ioctlsocket(sock,SIO_RCVALL,&dwVal);//设置网卡为混听模式inti=0;while(true){fromlen=sizeof(from);bytes_recieved=recvfrom(sock,buffer,sizeof(buffer),0,(structsockaddr*)&from,&fromlen);//接收数据i++;ip=(structip*)buffer;//得到ip头if(ip-proto==6)//过滤其他协议,只留下TCP协议{tcp=(structtcp*)(buffer+(4*ip-h_verlen&0xf04));//得到tcp头printf(Ip包字节数:%d\n,bytes_recieved);//打印ip数据包长度printf(源IP:%s\n,inet_ntoa(*(in_addr*)&ip-sourceIP));//打印源IPprintf(目的IP:%s\n,inet_ntoa(*(in_addr*)&ip-destIP));//打印目的6IPprintf(源端口:%d\n,ntohs(tcp-th_sport));//打印源端口printf(目的端口:%d\n,ntohs(tcp-th_dport));//打印目的端口printf(TCP的数据内容:);char*ptr=buffer+5+4*((tcp-th_lenres&0xf0)4|0);//计算数据头指针intcpysize=bytes_recieved-5-4*((tcp-th_lenres&0xf0)4|0);//计算数据长度memcpy(buffer,ptr,cpysize);//取出数据for(inti=0;icpysize;i++)//打印数据{if(buffer[i]=32&&buffer[i]255){printf(%c,(unsignedchar)buffer[i]);}else{printf(.);}}printf(\n);}}}运行界面:7四、总结与体会掌握了利用RAWSOCKET捕获网络数据包并对其进行分析

1 / 8
下载文档,编辑使用

©2015-2020 m.777doc.com 三七文档.

备案号:鲁ICP备2024069028号-1 客服联系 QQ:2149211541

×
保存成功