1.2 UDP协议
UDP是一种无连接、尽最大努力交付的运输层协议,不提供流量控制和确认机制,数据报可能丢失、延迟、乱序到达。这就是的UDP在实现起来就较为简单,这种简单能很好的应用在实时通信服务中,如实时语音传输、实时视频通信等。
下面给出基于UDP的c/s通信工作模式:
进程A 进程B
socket()建立套socket()建立套
接字 接字
bind()套接字与bind()套接字与
本地地址绑定 本地地址绑定
交换数据 recvform()接受sendto()发送数
数据 据
sendto()发送数据 交换数据 recvform()接受数据 close()关闭套接字 close()关闭套接字 基于udpP的c/s通信模式 1.3 套接字的定义
套接字我们可以认为就是通信的一端,其主要包括协议、ip、端口号。将两个套接字连接在一起就可以实现端到端的网络通信了。在套接字中封装了网络和传输层协议,从而为程序员屏蔽了底层通信的复杂性。
针对不同通信的需求,在TCP/IP协议中提供了3种不同套接字类型,分别为: 流式套接字(SOCK_STREAM)、数据保式套接字(SOCK_DGRAM)、原始套接字(SOCK_RAW)。
流式套接字(SOCK_STREAM) 提供面向连接的,可靠的数据传输服务,数据无差错,无重复的发送,且按发送的顺序接收,基于 TCP 协议。
- 4 - / 39
数据保式套接字(SOCK_DGRAM) 提供无连接的服务,数据包以独立包形式发送,不提供无错误的保证,数据可能丢失或重复,且接收顺序混乱,基于 UDP 协议。 原始套接字(SOCK_RAW) 主要是在编写自定义底层协议的应用程序时使用。
1.4 客户机/服务器模式的运行原理
网络应用程序一般是以客户机/服务器的模型的方式工作的。在这种工作方式中,一个服务器程序通常事先启动, 并在一个熟知端口侦听对服务器的请求。当客户机应用程序需要某种服务时,需向提供这种服务的服务器发出请求,服务器在接收到请求后,向客户机发出相应请求信息。这样 客户机应用程序和服务器程序之间便建立了通信连接, 此后可以进行数据通信。通信任务完成后需要关闭它们之间的通信连接。
2 系统设计
2.1 基于TCP应用程序设计:
发送/接受数据
服务器进程服务器进程发送/接受数据 客户机进程 2.2 基于UDP应用程序设计:
- 5 - / 39
登陆,注册信息到服务器 请求客户B的ip和端口信息 登陆,注册信息到服务器 请求客户A的ip和端口信息 客户机A进程 服务器进程 客户机B进程 3 详细设计
3.1基于TCP的应用程序设计: 3.1.1 服务器设计:
#include
int main(int argc, char *argv[]) {
const int DEFAULT_PORT = 5000; WORD wVersionRequested; WSADATA wsaData; int err,iLen;
wVersionRequested=MAKEWORD( 2, 2 );
err = WSAStartup( wVersionRequested, &wsaData ); if ( err != 0 ) {
cout<<\加载WinSock失败!\ return 0; }
//创建用于监听的套接字
SOCKET sockSrv = socket(AF_INET,SOCK_STREAM,0); //创建服务器监听套接字 if (sockSrv == INVALID_SOCKET) {
cout<<\ return 0; }
SOCKADDR_IN addrSrv; char cip[20]=\ int port; char type;
cout <<\服务器基本设置为 ip:127.0.0.1 端口:5000\ cout <<\是否从新设置:Y or N\
- 6 - / 39
cin>>type; if(type=='Y') {
cout<<\ cin>>cip; //ip=cip;
cout<<\端口:\ cin>>port;
addrSrv.sin_family = AF_INET;
addrSrv.sin_addr.S_un.S_addr = inet_addr(cip); addrSrv.sin_port = htons(port); } else {
addrSrv.sin_family = AF_INET;
addrSrv.sin_addr.S_un.S_addr = inet_addr(\ addrSrv.sin_port = htons(DEFAULT_PORT); }
//绑定本地主机IP和端口
err = bind(sockSrv,(SOCKADDR*)&addrSrv,sizeof(SOCKADDR)); if ( err != 0 ) {
cout<<\ return 0; }
cout<<\//监听
err = listen(sockSrv,5); if ( err != 0 ) {
cout<<\ return 0; }
cout<<\SOCKADDR_IN addrClient; int len = sizeof(SOCKADDR);
while(1) {
SOCKET sockConn = accept(sockSrv,(SOCKADDR*)&addrClient,&len);//接收客户
- 7 - / 39
相关推荐: