滑动窗口协议_第1页
滑动窗口协议_第2页
滑动窗口协议_第3页
滑动窗口协议_第4页
滑动窗口协议_第5页
已阅读5页,还剩5页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、/*接收端程序:#pragmacomment(lib,"ws2_32.lib")#include<winsock.h>#include<stdio.h>#include<time.h>/接收帧/BOOLReceiveFrame(int*frameExcept,int*frameRecv,intwinRecvSize,SOCKETsocket)charrecvBuffer128;/接收数据intframeNum;/接收帧号从发送端接收帧if(recv(socket,recvBuffer,sizeof(recvBuffer),0)=SOCKE

2、T_ERROR)printf("接收数据失败!n");returnFALSE;frameNum=atoi(recvBuffer);if(frameNum!=*frameExcept)/接收帧和希望接收帧号不匹配printf("所要接收的帧和接收到的帧不匹配!,要接收的帧号是:d,接收到的帧号是:dn",*frameExcept,frameNum);returnFALSE;else/腰收帧和希望接收帧号匹配*frameRecv=frameNum;printf("已经成功地接收帧d,接收端窗口大小是:dn",*frameRecv,winR

3、ecvSize);returnTRUE;/发送ACK/BOOLSendACK(int*frameExcept,int*frameRecv,SOCKETsocket)通过随机数随机产生正确ACK帧号、错误ACK帧号以及不发送ACK帧charsendBuffer128;/发送数据intrandom=0;/随机数0,1,2,0表示返回正确ACK1表示返回错误ACK2表示不返回ACKrandom=rand()%3;if(random=0)表示正确接收,并且正确回复ACK(if(_snprintf(sendBuffer,sizeof(sendBuffer)-1,"%d",*frame

4、Recv)<0)(printf("写数据出错!n");returnFALSE;else(sendBuffersizeof(sendBuffer)-1='0'发送正确的ACKif(send(socket,sendBuffer,sizeof(sendBuffer),0)=SOCKET_ERROR)(printf("发送数据失败!n");returnFALSE;else(*frameExceptA=1;/经过确认,准备接受下一帧printf("针对已经接收到的帧d回复ACK,回复的ACK号是%d:nn",*frameR

5、ecv,*frameRecv);elseif(random=1)/表示正确接收,并且错误回复ACK(if(_snprintf(sendBuffer,sizeof(sendBuffer)-1,"%d",(*frameRecv)A1)<0)(printf("写数据出错!n");returnFALSE;else(sendBuffersizeof(sendBuffer)-1='0;发送错误的ACKif(send(socket,sendBuffer,sizeof(sendBuffer),0)=SOCKET_ERROR)(printf("发送

6、数据失败!n");returnFALSE;)else(printf("针对已经接收到的帧d回复ACK,回复的ACK号是%d:nn",*frameRecv,(*frameRecv)A1);)else/加示正确接收,并且不回复ACK(/不发送ACKprintf("没有针对已经接收到的帧%d发送ACKnn",*frameRecv);)returnTRUE;)/初始化发送端监听socket/BOOLInitSocketReceiver(SOCKET*socketRecv)(WORDwVersionRequested;WSADATAwsaData;SOC

7、KADDR_INaddrSender;intlength=sizeof(structsockaddr);/版本wVersionRequested=MAKEWORD(1,1);/启动if(WSAStartup(wVersionRequested,&wsaData)!=0)(printf("启动socket不成功!n");returnFALSE;)if(LOBYTE(wsaData.wVersion)!=1|HIBYTE(wsaData.wVersion)!=1)(printf("版本错误!n");WSACleanup();returnFALSE;)

8、/创建socket*socketRecv=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);if(socket=INVALID_SOCKET)(printf("创建套接字失败!n");returnFALSE;创建地址信息addrSender.sin_addr.S_un.S_addr=inet_addr("127.0.0.1");/发送端主机IPaddrSender.sin_family=AF_INET;addrSender.sin_port=htons(8000);/端口连接发送端if(connect(*socketRecv

9、,(structsockaddr*)&addrSender,length)=SOCKET_ERROR)(printf("连接服务器失败!n");WSACleanup();returnFALSE;returnTRUE;voidmain()(SOCKETsocketRecv;/接收端socketintframeExcept=0;/期待的帧号intwinRecvSize=1;窗口大小intframeRecv=0;接收的帧号intcount=0;/循环次数计数器BOOLrecvFlag=FALSE;/是否正确接收帧连接服务器if(!InitSocketReceiver(&a

10、mp;socketRecv)(printf("初始化客户端失败,退出!n");WSACleanup();return;else(%d,准备接收发送端数据nn",winRecvSize);printf("已经成功连接服务器nn");printf("初始状态接收端窗口大小是:srand(unsigned)time(NULL);while(count<20)(recvFlag=ReceiveFrame(&frameExcept,&frameRecv,winRecvSize,socketRecv);if(recvFlag

11、)正确接收帧,发送ACK(SendACK(&frameExcept,&frameRecv,socketRecv);else(printf("得到错误的帧!n");+count;printf("模拟结束!n");清理closesocket(socketRecv);WSACleanup();system("pause");/*发送端程序:#pragmacomment(lib,"ws2_32.lib")#include<winsock.h>#include<stdio.h>/发送帧

12、/voidSendFrame(int*frameNumCurrent,intwinSizeCurrent,SOCKET*socketConn)(charsendBuffer128;/发送数据if(_snprintf(sendBuffer,sizeof(sendBuffer)-1,"%d",*frameNumCurrent)<0)(printf("写数据出错!n");return;else(sendBuffersizeof(sendBuffer)-1='0')发送数据第几帧if(send(*socketConn,sendBuffer,

13、sizeof(sendBuffer),0)=SOCKET_ERROR)(printf("发送数据失败!n");return;)else(printf("现在在传送帧%sn",sendBuffer);)/接收ACK/voidReceiveACK(int*frameNumCurrent,SOCKET*socketConn)(charrecvBuffer128;/接收数据intlength=sizeof(structsockaddr);intframeNum=0;/接收到的ACK号/接收ACK,判断是否有超时或者是否错误ACKif(recv(*socketCo

14、nn,recvBuffer,sizeof(recvBuffer),0)=SOCKET_ERROR)/出现超时(printf("接收数据超时!需要重新传送帧dnn",*frameNumCurrent);return;)else(frameNum=atoi(recvBuffer);正确ACKif(frameNum=*frameNumCurrent)(/正确ACK准备传送下一帧*frameNumCurrentA=1;printf("接收到正确的ACK,已经成功传送帧d,将要传送帧dnn",(*frameNumCurrent)A1,*frameNumCurren

15、t);)错误ACKelseif(frameNum=(*frameNumCurrent)人1)/得到错误ACK不进行操作,主函数中进行重传操作printf("接收到错误ACK,帧d传送错误,需要重新传送帧dnn",*frameNumCurrent,*frameNumCurrent);)/初始化发送端监听socket/BOOLInitSocketSender(SOCKET*socketSender)(SOCKADDR_INaddrSender;WORDwVersionRequested;WSADATAwsaData;/版本wVersionRequested=MAKEWORD(1

16、,1);/启动if(WSAStartup(wVersionRequested,&wsaData)!=0)(printf("启动不成功!n");returnFALSE;)if(LOBYTE(wsaData.wVersion)!=1|HIBYTE(wsaData.wVersion)!=1)(printf("版本错误!n");WSACleanup();returnFALSE;)/创建socket*socketSender=socket(AF_INET,SOCK_STREAM,0);if(*socketSender=INVALID_SOCKET)(pri

17、ntf("创建套接字失败!n");returnFALSE;)创建地址信息addrSender.sin_addr.S_un.S_addr=htonl(INADDR_ANY);/所有地址addrSender.sin_family=AF_INET;addrSender.sin_port=htons(8000);端口号绑定端口if(bind(*socketSender,(SOCKADDR*)&addrSender,sizeof(structsockaddr)SOCKET_ERROR)printf("绑定失败!n");returnFALSE;/监听if(l

18、isten(*socketSender,SOMAXCONN)=SOCKET_ERROR)printf("监听失败!n");returnFALSE;returnTRUE;/线程函数用于处理一个客户端请求/DWORDWINAPIConnectClient(LPVOIDsocketConn)intcount=0;/循环次数计数器intwinSizeCurrent=0;/当前发送窗口大小intframeNumCurrent=0;/当前发送的帧号printf("初始状态发送窗口是:d,准备向接收端发送数据nn",winSizeCurrent);+winSizeCu

19、rrent;while(count<20)SendFrame(&frameNumCurrent,winSizeCurrent,(SOCKET*)socketConn);ReceiveACK(&frameNumCurrent,(SOCKET*)socketConn);+count;printf("模拟结束!n");关闭Socketclosesocket(*(SOCKET*)socketConn);free(socketConn);return0;voidmain()HANDLEhThread;/线程句柄DWORDthreadId;SOCKETsocketSender;/监听socketSOCKADDR_INaddrReceiver;/服务器地址intlength=sizeof(structsockaddr);inttimeOut=3000;/超日3秒初始化发送端监听socketif(!InitSocket

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论