最近在看Tomcat
源码,涉及到网络编程模型,所以将这块的知识点进行一个归纳整理。
网络是由若干节点(计算机)和连接这些节点的链路构成,表示诸多对象及其相互联系。
网络的主要功能就是资源共享。共享的资源包括软件资源、硬件资源以及存储在公共数据库中的各类数据资源。网上用户能部分或全部地共享这些资源,使网络中的资源能够互通有无、分工协作,从而大大提高系统资源的利用率。
分布在不同地区的计算机系统,可以通过网络及时、高速地传递各种信息,交换数据,发送电子邮件,使人们之间的联系更加紧密。
在网络中,由于计算机之间是互相协作、互相备份的关系,以及在网络中采用一些备份的设备和一些负载调度、数据容错等技术,使得当网络中的某一部分出现故障时,网络中其他部分可以自动接替其任务。因此,与单机系统相比,计算机网络具有较高的可靠性。
在网络中,还可以将一个比较大的问题或任务分解为若干个子问题或任务,分散到网络中不同的计算机上进行处理计算。这种分布处理能力在进行一些重大课题的研究开发时是卓有成效的。
在当今的信息化社会里,个人、办公室、图书馆、企业和学校等,每时每刻都在产生并处理大量的信息。这些信息可能是文字、数字、图像、声音甚至是视频,通过网络就能够收集、处理这些信息,并进行信息的传送。因此,综合信息服务将成为网络的基本服务功能。
1、按拓扑结构分类:总线型、环型、星型、网状
2、按信息交换方式分类:电路交换、报文交换、报文分组交换
3、按覆盖范围分类:局域网LAN
、广域网WAN
局域网:局部区域网络(local area network)通常简称为"局域网",缩写为LAN。局域网是结构复杂程度最低的计算机网络。局域网仅是在同一地点上经网络连在一起的一组计算机。局域网通常挨得很近,它是如今应用最广泛的一类网络。
广域网:广域网网络(wide area network)又称外网、公网。是连接不同地区局域网或城域网计算机通信的远程网。
TCP/IP
协议(Transfer Control Protocol/Internet Protocol
)叫做传输控制/网际协议,又叫网络通讯协议,它包括上百个各种功能的协议,而TCP协议和IP协议是保证数据完整传输的两个基本的重要协议。
通常说TCP/IP
是Internet协议簇,而不单单是TCP
和IP
TCP/IP
协议的基本传输单位是数据包(Datagram)。TCP
协议负责把数据分成若干个数据包,并给每个数据包加上包头;IP
协议在每个包头上再加上接收端主机地址,
这样数据找到自己要去的地方。如果传输过程中出现数据丢失、数据失真等情况,TCP
协议会自动要求数据重新传输,并重新组包。总之,IP
协议保证数据的传输,TCP
协议保证数据传输的质量
TCP/IP
协议数据的传输基于TCP/IP
协议的四层结构:应用层(应用层、表示层、会话层)、传输层、网络层、网络接口层(数据链路层、物理层),数据在传输时每通过一层就要在数据上加个包头,
其中的数据供接收端同一层协议使用,而在接收端,每经过一层要把用过的包头去掉,这样来保证传输数据的格式完全一致。如下为4层(包含OSI
七层)示意图:
Internet
依靠TCP/IP
协议,在全球范围内实现不同硬件结构、不同操作系统、不同网络系统的互联。在Internet
上,每一个节点都依靠的IP
地址互相区分和相互联系。
IP
地址是一个32位二进制数的地址,由4个8位字段组成,每个字段之间用点号隔开,用于标识TCP/IP
宿主机。
在linux
系统中有一句话:一切皆文件 ,文件就是流的概念,在进行信息的交流过程中,对这些流进行数据的收发
操作就是IO
操作。
不管socket
、管道、终端,对Linux
来说,一切都是文件,一切都是流。在信息 交换的过程中,我们都是对这些流进行数据的收发操作,
简称为I/O
操作(input and output
),往流中读出数据,系统调用read
,写入数据,系统调用write
。值得一提的是计算机里有这么多的流,
怎么知道要操作哪个流呢?这里就有可文件描述符的概念,即通常所说的fd
,一个fd
就是一个整数,所以,对这个整数的操作,就是对这个文件(流)的操作。
我们创建一个socket
,通过系统调用会返回一个文件描述符,那么剩下对socket
的操作就会转化为对这个描述符的操作。
所谓同步就是每件事情必须有回应才能进行下一件事情,也就是说必须一件一件的事情来做。如下图:
所谓异步就是客户端发送完事件后可以干其他的事情,可以继续发送其他的请求,等到服务端处理完成后,通过 回调将结果告知客户端就可以。如下图:
所谓阻塞就是在请求没有处理完成之前,线程一直处于等待的状态,直到线程处理完成后才给返回结果。
所谓非阻塞就是在请求没有处理完成之前,直接返回结果。不用等到线程处理完成之后才有响应。
所有的套接字默认都是阻塞的,它要等到有 数据包到达并且被复制到应用程序的进程缓冲区中或者出现了异常 才被返回 否则一直阻塞。模型如下图:
原理:用户线程通过系统调用read发起IO读操作,由用户空间转到内核空间。 内核等到数据包到达后,然后将接收的数据拷贝到用户空间,完成read操作。
非阻塞IO
通过进程反复调用IO
函数(多次系统调用,并马上返回),知道等待待成功的通知。如下图:
原理:由于socket是非阻塞的方式,因此用户线程发起IO请求时立即返回。 但并未读取到任何数据, 用户线程需要不断地发起IO请求,直到数据到达后,才真正读取到数据,继续执行。
可以通过系统调用select、poll、epoll
实现IO
复用模型。此时进程就会组赛在这些系统调用上,而不是阻塞在真正的IO
操作上,
直到有就绪事件了,这些系统调用就会返回哪些套接字可读写,然后就可以进行把数据包复制到应用进程缓冲区了
IO
多路复用模型是建立在内核提供的多路分离函数select
基础之上的,使用select
函数可以避免同步非阻塞IO模型中轮询等待的问题。如下图:
原理:将需要进行IO操作的socket添加到select中,然后阻塞等待select系统调用返回。 当数据到达时,socket被激活,select函数返回。用户线程正式发起read请求,读取数据并继续执行。
由用户进程告知内核启动一个操作,并且由内核去操作,操作完后给用户进程发一个通知,通知用户进程操作完了。如下图
异步IO模型中,当用户线程收到通知时,数据已经被内核读取完毕,并放在了用户线程指定的缓冲区内,内核在IO完成后通知用户线程直接使用即可
以上的相关概念是作者认为学习网络编程中,我们应该知道的一些概念。我们在学习以后的内容的时候,都是以这些为基础的。