收藏 分销(赏)

UNIX网络的服务器程序设计方法.docx

上传人:pc****0 文档编号:8905404 上传时间:2025-03-07 格式:DOCX 页数:11 大小:23.03KB 下载积分:10 金币
下载 相关 举报
UNIX网络的服务器程序设计方法.docx_第1页
第1页 / 共11页
UNIX网络的服务器程序设计方法.docx_第2页
第2页 / 共11页


点击查看更多>>
资源描述
UNIX网络的服务器程序设计方法 (刘凯 刘春旭,四川大学计算机学院) 摘要:介绍了几种网络操作模式和UNIX下基于TCP/IP协议的网络客户/服务器模式的程序架构。重点对客户/服务器模式中服务器程序的几种设计方法进行了讨论。 关键词:客户/服务器,Socket,进程,并发服务器 1.引言 1.1几种网络模式的介绍 对等网络(Peer-to-Peer)模式不需要专用服务器,每一台工作站都能充当网络服务的请求者和提供者,都有绝对自主权,也可以互相交换文件。这种类型的网络软件被设计成每一个实体都能完成相同或相似的功能。 服务器(Server-Based)模式以服务器为中心,严格地定义了每一个实体的工作角色,即网络上的工作站无法在彼此间直接进行文件传输,需通过服务器作为媒介,所有的文件读取,消息传送等也都在服务器的掌握之中。 客户/服务器(Client/Server)模式(有时也称为主从式Master/Slave)指将需要处理的工作分配给客户端和服务器端处理,所谓的客户和服务器并没有一定的界限,这取决于运行什么软件,简单的讲,客户是提出服务请求的一方,而服务器是提供服务的一方。在客户/服务器模式中服务器端所提供的功能不仅仅是文件、数据库等服务,还应当有相应的计算、通信等能力——也就是说在工作时由客户端和服务器端各自负担一部分计算或通信的功能。客户/服务器模式已经成为计算机网络互连中最重要的应用技术之一,它把一个大型的计算机应用系统变为多个能互为独立的子系统,而服务器便是整个应用系统资源的存储与管理中心,多台客户机则各自处理相应的功能,共同实现完整的应用。 浏览器/服务器(Browser/Server)模式从本质上将,仍然是客户/服务器模式(是客户/服务器模式的特例)。只不过在某些应用方面,如数据库服务,它将传统的二层客户/服务器结构发展成三层的客户/服务器结构并在Internet上应用而已。 在上述几种模式中,客户/服务器模式具有灵活多变的体系结构、丰富的开发环境和强大的设备驱动能力。 1.2本文所采用的网络应用程序编程接口 网络程序之间进行通讯,必须建立在一定的通讯协议基础之上。对于UNIX下的应用程序,可用的协议有TCP/IP的传输控制协议TCP(Transmission Control Protocol)和用户数据报协议UDP(User Datagram Protocol),XNS(Xerox Network System)的定序分组协议SPP(Sequential Pocket Protocol)和网际数据报协议IDP(Internetwork Datagram Protocol)以及ARPANET的接口报文处理机链路IMPLINK(Interface Message Processor Link)等。因为Internet的普及,使得TCP/IP成为使用最广泛的协议。 UNIX下基于TCP/IP协议的网络应用程序编程接口API(Application Programming Interface)有两种:源自BSD UNIX的Socket API和AT&T的传输层接口TLI(Transport Layer Interface)的超集——X/Open传输接口XTI(X/Open Transport Interface)。这两种API都是面向客户/服务器模式的。由于Socket API已经成为事实上的标准,因此本文在介绍服务器端程序的设计方法时也采用Socket API。 2.客户/服务器模式的Socket实现框架 2.1 TCP/IP Socket的基本原理。 TCP/IP对外提供的只是编程接口而非用户服务,真正的用户服务还得靠编写相应的服务程序来实现。TCP/IP的Socket API编程接口构成了使用协议的网络应用程序视图。 服务程序 客户程序 Socket API TCP/IP协议 物理介质 图1.网络应用程序、Socket API和TCP/IP的关系 Socket API在BSD UNIX中首次提出,其目的是为了解决网络间程序通讯的问题。就其原理而言,面向连接的Socket类似于电话系统,无连接的Socket类似于电报系统。Socket实质上是为网络程序提供了通讯的端点号。对于每个网络程序的一个Socket,它首先有一个半相关的端点号的描述:{协议,本地地址,本地端口},如果它是与另一个Socket连接了的,则有一个相关的端点描述:{协议,本地地址,本地端口,远程地址,远程端口}。每个Socket有一个本地唯一的由操作系统分配的编号。 2.2 Socket 的系统调用 Socket是面向客户/服务器模式设计的,它针对客户和服务器程序提供了不同的系统调用。同时它还分为面向连接和无连接两种类型。下表列出了Socket API的基本函数(这里就不对调用参数进行说明了)。 表1 基本的Socket系统调用 函数名 用途 使用者 相关协议 说明 socket 建立一个通讯端点 客户、服务器 TCP、UDP bind 为一个连接的本地socket赋名 客户、服务器 TCP、UDP 使用TCP时,使用者为服务器;使用UDP时,使用者为客户 listen 监听socket上的连接 服务器 TCP accept 接受socket上的连接 服务器 TCP connect 对socket进行连接初始化 客户 TCP read 从socket接收信息 客户、服务器 TCP write 向socket发送信息 客户、服务器 TCP recvfrom 从socket接收信息 客户、服务器 UDP sendto 向socket发送信息 客户、服务器 UDP close 关闭socket 客户、服务器 TCP、UDP 2.3面向连接和无连接的客户/服务器模式的程序流程框架图 服务器 socket ( ) 服务响应 服务请求 建立连接 处理服务请求 bind ( ) listen ( ) accept ( ) 阻塞并等待客户的连接请求 read ( ) write ( ) 客户 socket ( ) connect ( ) write ( ) read ( ) 图2. 面向连接的客户/服务器模式 服务器 服务响应 服务请求 bind() recvfrom() 阻塞并等待客户数据 处理服务请求 sendto() socket() 客户 recvfrom() sendto() bind() socket() 图3 无连接的客户/服务器模式 3.服务器程序的设计方法 3.1总述 客户程序一般比较简单,而服务器程序就比较复杂了,因为对服务器程序的设计,必须考虑到其响应速度和响应能力等服务性能因数。本文主要讨论的是面向连接的服务器程序设计方法。 总体上服务器程序可分为两类:并发服务器(Concurrent Server)和串行服务器(Iterative Server)。前者主要针对实时性的客户/服务器模式,后者主要针对服务量小的客户/服务器模式。 3.2 TCP串行服务器程序 串行服务器程序是这样的:每次它只能为一个连接过来的客户程序提供服务,只有在完全处理了一个客户的请求后,才能响应下一个客户的请求,即按照FIFO的原则响应请求。一般很少使用串行服务器程序,不过诸如时间/日期等服务量小的且实时性要求不高的服务器程序可以使用该方式。从进程控制的角度来讲,该方式的速度是最快的,因为它不进行进程控制,系统开销小。 3.3 传统的TCP进程并发服务器程序 在这种方式下,并发服务器程序在收到客户程序请求后,派生出一个子进程来为该客户程序服务,自己则回到等待状态,准备接收下一个客户程序的请求,子进程在服务完成后退出。其中,作为父进程的并发服务器程序成为主服务器(master),具体处理客户请求的子进程成为从服务器(slave)。 响应 子进程接管连接 客户程序 slave 服务请求 父进程返回 生成子进程 fork() 连接 connect() 处理请求 master 接受客户请求 accecp() 图4 传统的TCP进程并发服务器程序框架 并发服务器的问题在于派生子进程(fork()操作)时会消耗CPU的很多时间,这对需要响应数目众多的客户进程的服务器进程所在的系统是极为不利的,例如对于Web服务器就是这样。 3.4 TCP预先派生子进程并发服务器程序 在传统的TCP进程并发服务器程序的基础上,可以对响应方式进行一些改造。传统的TCP进程并发服务器程序的响应方式是即响应即派生子进程。现在将这种方式改变为:服务器程序启动后就先生成若干子进程以备响应,这些子进程构成服务子进程组,而父进程则成了监控进程。 fork 可用子进程组 ... 父进程 子进程1 子进程2 子进程3 客户2 客户1 子进程N 图5 TCP预先派生子进程 这里需要解决的问题是:怎样保持一定量的可用子进程;服务请求到达时,唤醒子进程的机制应该怎样以及父进程怎样将必要的信息传递给子进程。 父进程监视可用子进程的数量,当数量低于某个阈值时就再派生一些子进程,当数量高于某个阈值时就终止一些可用子进程。当然,总的子进程数量也应当有个上限值,以防止系统资源消耗完。这样就使得可用子进程数及总的子进程数保持在一定范围之内了。 预先生成得子进程在各自调用accept()后进入睡眠状态。由于这些子进程共用一个socket结构,当一个可户请求到达时,就会造成惊群(thundering herd)——唤醒所有的子进程。当然,只有最先被调度的子进程才会获得客户的连接,其他的子进程会再次进入睡眠状态。这种情况会导致系统性能的下降。解决这个问题的方法是给accept上锁,即保证accept操作的原子性。有些UNIX系统在内核已经解决了这一问题,就无须再给accept上锁了。 如果子进程只是父进程的副本,基本上就不用额外考虑进程通讯的问题了。如果将父进程改造成类似于inetd的守护进程(启动后先调用fork()生成子进程,再通过exec系统调用执行服务处理程序),就必须解决父进程同子进程之间的通讯问题。UNIX下进程通讯的机制有多种,如管道(pipe),具名管道(named pipe),IPC消息(InterProcess Communication Message)等。这里我们使用IPC消息队列来向子进程传递socket描述字。 消息队列 客户1 客户2 父进程 子进程1 子进程2 子进程3 ... 可用子进程组 子进程N 图6 使用IPC消息机制的TCP预先派生子进程方法 3.5 TCP线程并发服务器程序 线程的执行效率比进程高10到100倍。编写线程函数时必须注意函数的线程安全性。并非所有的UNIX系统或同种UNIX的不同版本都支持线程。由于在方法上线程服务器程序同进程服务器程序的设计差不多,这里就不作多的描述了。 4.结束语 编程人员在编写具体的服务器程序时,应当结合具体的应用、网络结构和网络性能等情况,尽可能地提高服务效率和网络安全性。 参考文献 [1]《网络操作系统的分类》 [2]W.Richard Stevens 《UNIX网络编程(第1卷)》 清华大学出版社 1999年7月 [3]蔡传俊《UNIX/TCP/IP/NFS网络编程与应用开发》海洋出版社 1993年1月 [4]周明天 汪文勇《TCP/IP网络原理与技术》清华大学出版社 1997年2月 通讯地址:四川省成都市四川大学西区自动化系 刘玉生 转 610065 email:kai.liu@
展开阅读全文

开通  VIP会员、SVIP会员  优惠大
下载10份以上建议开通VIP会员
下载20份以上建议开通SVIP会员


开通VIP      成为共赢上传

当前位置:首页 > 包罗万象 > 大杂烩

移动网页_全站_页脚广告1

关于我们      便捷服务       自信AI       AI导航        抽奖活动

©2010-2025 宁波自信网络信息技术有限公司  版权所有

客服电话:4009-655-100  投诉/维权电话:18658249818

gongan.png浙公网安备33021202000488号   

icp.png浙ICP备2021020529号-1  |  浙B2-20240490  

关注我们 :微信公众号    抖音    微博    LOFTER 

客服