第3章基于TCP/IP协议的网络编程建立Winsock规范的主要目的是提供一个与协议无关的传送接口。本章介绍基于TCP/IP协议的Winsock网络编程技术,主要介绍TCP/IP协议的原理,Winsock基本概念与编程接口,WinsockAPI接口函数、数据结构及编程方法等。3.1协议概述TCP/IP是发展至今最成功的通信协议之一。它起源于20世纪60年代末美国政府资助的一个分组交换网络研究项目ARPRANET,其目的是允许分布在各地的装着完全不同的操作系统的计算机互相通信。TCP/IP以其开放性的特点,成为了INTERNET的基础。3.1协议概述TCP/IP协议是一个四层协议:链路层:ARP协议和RARP协议网络层:IP协议、ICMP协议、IGMP协议传输层:TCP协议、UDP协议应用层:Telnet、HTTP、SMTP、FTP等3.1.1IP协议IP层作为通信子网的最高层,提供无连接的数据报传输机制。IP协议主要解决的问题:路由选择IP层通过IP数据报和IP地址屏蔽各种网络的低层细节(如帧格式、地址格式等),为上层协议提供统一的格式IP数据报对物理帧的统一,IP数据报格式见60页IP地址对物理地址的统一3.1.2传输层协议TCP/IP协议簇中在传输层有两个并列的协议:TCP和UDP。TCP提供面向连接的流传输;UDP提供无连接数据报传输TCP提供高可靠性服务;UDP提供高效率服务TCP用于一次传输要交换大量报文的情形;UDP用于一次传输交换少量报文的情形,其可靠性由应用程序提供。具体选择取决于应用环境和需求。(1)TCP协议TCP协议是建立在IP协议之上的,IP不提供任何可靠性机制,所以TCP可靠性完全由自己实现。(1)数据传输前,通信双方必须建立一条连接(2)数据传输过程中,每一个报文都需要接收端确认,未确认的报文被认为是出错报文,发送方需要进行重传。TCP采用最基本的可靠性技术是:确认和重传。(2)UDP协议UDP协议几乎直接建立在IP协议之上,相对于IP协议,它唯一增加的能力是提供协议端口(Port),以保证进程通信。发送数据时,UDP软件构造一个数据报,然后将它交给IP软件,便完成所有的工作接收数据时,UDP软件先要判断所收到数据报的目的端口是否与当前使用的某端口匹配,如果是,则将数据报放入相应接收队列,否则抛弃该数据报,并向发送方发送“端口不可到达”ICMP报文3.2地址使用TCP/IP协议的互联网使用了3个等级的地址,分别对应在不同层上使用:物理地址(MAC地址)——网络接口层逻辑地址(IP地址)——网络层端口地址(PORT地址)——传输层IP地址屏蔽不同网络的物理地址差异,为上层提供了统一的地址格式,使设计者可以在不考虑物理硬件细节的情况下自由地选择地址。3.2.1物理地址与IP地址物理地址:包含在数据链路层使用的帧中,是最低一级的地址,该地址的长度和格式是可变的,取决于网络种类。IP地址:IP地址标识一台计算机和网络之间的一个连接。32位IP地址被分割为两个部分:前缀(网络标识):确定计算机所从属的物理网络后缀(主机标识):确定网络上某一台计算机注意:当网络设备从一个网络移动到另一个网络时,该设备的物理地址保持不变,但要相应地改变它的IP地址。物理地址与IP地址的映射——地址解析地址解析:就是将计算机的IP地址翻译成物理地址,地址解析只能在本地网中进行。ARP协议:从IP地址到物理地址的映射RAPR协议:从物理地址到IP地址的映射3.2.2端口地址若不同主机上的两个进程A和B进行通信,我们假定进程A想要向进程B发送数据,那么进程A必须知道B进程的地址,这个地址包括:网络地址(IP地址)端口号(PortNumber)每个应用程序都必须有一个或多个端口号来接收由TCP或UDP送来的数据IP地址让IP可将数据送至正确的主机TCP或UDP协议应用程序3应用程序2应用程序1应用程序n……Port1PortnPort2……Port3你的上网计算机……Web网站POP3服务器(收信)SMTP服务器(发信)Windows计算机UnixLinux主机Port80Port110Port25Port139Port23TCP/IP协议(Protocol)Internet世界TCP/IP协议(Protocol)Windows系统Port80Port110Port25Port139Port23Port??……IEOutlookExpress资源管理器Telnet各种网络软件连接远程的各种服务器、主机或一般个人电脑从上图中可以看出,端口是电脑进出Internet的大门,任何一个应用程序都必须打开一个(或数个)门(端口)之后才能与Internet世界沟通,当任何一个程序退出时也必须将所打开的端口全部关闭才行。定义:端口用于标识通信主机中不同的通信进程,作为UDP和TCP数据报头的一部分传输。各个通信进程通过系统调用与某些端口建立绑定,传输层传送到该端口的所有数据相应地被与其绑定的进程接收。端口号(PortNumber):每个端口都是用端口号来标识的。在TCP和UDP协议中,端口号是一个16位的整数值,即可以提供65536(216)个端口。注意:端口和协议在进程通信中是密不可分的,不同协议的端口之间没有任何联系。例如TCP和UDP协议的端口号相互独立的,若TCP有一个1001号端口,同样UDP也可以有一个1001号端口,它们并不冲突。端口号的分配问题:TCP/IP将全部端口号分为保留端口号和自由端口号两部分。保留端口号(1~1023):以静态方式进行分配,由IANA进行管理。TCP和UDP协议都规定,把1~255之间的端口号作为保留端口,对应一些通用的应用层协议(如下图);而256~1023之间的端口通常由UNIX系统占用,提供一些特定的UNIX服务。TCP保留端口号举例:端口23端口说明端口21FTP文件下载上传服务Telnet主机连接服务端口25SMTP发信服务端口80HTTP网页服务端口110POP3收信服务端口139NetBIOS网上邻居、资源管理器连接服务自由端口(1024~65535):占全部端口的绝大部分,以动态方式进行分配(即应用程序根据自己的需要向操作系统申请,由系统进行管理)这样,当一个进程要与远地进程通信时,需要先申请一个自由端口号,然后根据静态分配的保留端口号或双方协商好的端口号与远地进程建立连接,才能传输数据。3.3客户机/服务器模式在TCP/IP网络应用中,通信的两个进程间相互作用的主要模式是客户机/服务器模式(Client/ServerModel):服务器是一个进程,它一直等待着客户进程的请求以便为客户进程服务;客户进程向服务器提出请求,服务器对请求做相应的处理并执行被请求的任务,然后将结果返回给客户机。客户机/服务器模式的建立基于以下两点:首先,建立网络的起因是网络中软/硬件资源、运算能力和信息不均等,需要共享,从而形成拥有众多资源的主机提供服务,资源较少的客户请求服务这一非对称的情况。其次,网间进程通信完全是异步的,相互通信的进程间既不存在父子关系,又不共享内存缓冲区,因此需要一种机制为需要通信的进程间建立联系,为二者的数据交换提供同步。客户机/服务器模型工作时要求有一套协议来保证保证服务能够被提供,协议必须在通信的两端——客户机和服务器都被实现。根据实际情况,协议可以是对称的,也可以是非对称的。对称的:每一方都有可能扮演主从角色。如Internet中用于终端仿真的Telnet非对称的:一方不可改变地被认为是主机,而另一方则是从机。如Internet中的HTTP。客户机/服务器模式的工作步骤:服务器进程开始执行,首先初始化本身,然后进入睡眠状态以等待客户进程的请求。通常是在一个众所周知的地址(如FTP:21)侦听客户对服务的请求在本系统或与服务器相连的其他系统上,某一个客户进程开始执行,把请求发送给服务器进程请求服务服务器进程“惊醒”并且为客户提供服务,作出适当的反应。从上面描述的过程可知:客户机与服务器进程的作用是非对称的,因此编码不同。服务进程一般是先于客户机请求而启动的,只要系统运行,该服务进程一直存在,直到正常终止或强迫终止。3.4Winsock介绍套接字(Socket)的来源:最早被用于BerkeleySoftwareDistribution(BSD)的UNIX系统中,随着UNIX的广泛使用,Socket成为最通用的网络设计接口。3.4.1socket的来源WindowsSockets:Winsock程序接口,它定义了一套可使网络程序开发人员在Windows环境下开发标准TCP/IP网络程序。Winsock继承了BerkeleySocket的主要特征,同时进行了重要扩充,有利于程序员开发出符合Windows编程模式的软件。Winsock接口包含了一组网络I/O和获取网络信息的库函数,网络程序通过调用这部分函数实现自己的功能:Winsock1.1的库函数在Winsock.dll动态链接库Winsock2.0的库函数在Ws2_32.dll动态链接库Winsock定义了如何使用API与Internet通讯协议(TCP/IP协议)的连接:应用程序调用Winsock的API实现相互之间的通信,而Winsock则利用下层的网络通信协议功能与操作系统调用实现实际的通信工作。它们之间的关系如图:应用程序1应用程序2应用程序N网络编程接口(Winsock)网络通信服务接口(TCP/IP)操作系统(Windows)硬件接口(网卡)3.4.2Winsock的基本概念(1)套接字(Socket)Socket是通信的基石,是支持TCP/IP协议网络通信的基本操作单元。一个Socket就是一个通信的端点,用以一个短整数来表示。注意:Socket不是端口号,它只是一个句柄,代表网络协议中的一组数据,这组数据包括TCP连接中双方的IP地址以及目前连接状况等。一个正在被使用的Socket都有它的类型和与其相关的网络应用进程。根据通信性质,Socket可以分为两类:StreamSocket(会话套接字):使用TCP协议,提供一种面向连接的可靠数据通信方式。当要发送大批量数据或想让发出的数据按顺序无重复地到达目的地时,就要使用会话套接字,但需要很多开销。DatagramSocket(数据报套接字):使用UDP协议,提供不可靠的、非连接的数据通信方式,具有向多个目标地址发送广播数据报的能力,由于其并不十分可靠,需要应用程序负责管理数据报的排序和可靠性。总之,若要用TCP协议那Socket就必须设为Stream,反之,用UDP就设为Datagram。3.4.2Winsock的基本概念(2)广播使用数据报套接字可以向网络发送广播数据。TCP/IP协议支持一个标记地址——INADDR_BROADCAST用于广播。广播通常应用于两种情况:一是应用程序希望在本地网络中找到一个资源,而事先不知道该资源的地址一些重要的信息需要发送给网中所有计算机3.4.2Winsock的基本概念(3)字节顺序计算机世界主要采用两种字节顺序来存储数据:①“Litter-Endian”位顺序:是指一个字(Word)在内存中的排列方式是低字节在高字节之前,通常也称作低字节顺序、主机字节顺序。例如,Intel处理器的字节顺序就是“Litter-Endian”。②“Big-Endian”位顺序:则是高字节在前,而低字节在后,通常也称作高字节顺序、网络字节顺序。例如,Internet网络的字节顺序就是“Big-Endian”。任何Windsock函数对IP地址和端口号的使用以及传送给Winsock函数的IP地址和端口号均是按照“Big-Endian”(网络字节)顺序组织的。Intel处理器和Internet网络的字节顺序不同,因此两种顺序的转换是无法避免的,例如:情况一:当用户输入一个数值,而且指定使用该数值作为端口号(此时该数值的存储是采用主