CSAPP–第十一章–网络编程(上)

Aki 发布于 2023-01-30 185 次阅读


客户端-服务器编程模型

每个网络应用都是基于客户端-服务器编程模型,一个应用是由一个服务器进程和一或多个客户端进程组成,服务器管理资源,并通过操作这种资源来为他的客户端提供某种服务(web 服务器管理一组磁盘文件,它会代表客户端进行检索和执行)。

客户端-服务器编程模型中的基本操作都是事务(transaction),由以下四部分组成:(1)当一个客户端需要服务时,它向服务器发送一个请求,发起一个事务;(2)服务器收到请求后,解释它并以适当的方式操作它的资源;(3)服务器给客户端一个响应,等待下一个请求;(4)客户端收到响应并处理。

网络、

客户端和服务器通常运行在不同主机,通过计算机网络的硬件和软件资源来通信。对主机而言网络只是一种 IO 设备,是数据源和数据接收方,一个插到 IO 总线扩展槽的适配器提供了网络的物理接口。从网络上接收到的数据从适配器经过 IO 总线复制到内存,通常通过 DMA 传送,同时数据也能从内存复制到网络适配器,然后发送到网络上。

全球 IP 因特网、

每台主机都运行 TCP/IP 协议(Transmission Control Protocol / Internet Protocol,传输控制协议/互联网网络协议)。客户端和服务器混合使用套接字接口函数(Socket)进行通信。SOCKET 典型的作为会陷入内核的系统调用实现。

IP 协议提供基本的命名方法和传送机制;从某种意义上来说是不可靠的,因为,如果丢失或者重复,并不会试图恢复。UDP 扩展 IP 协议,包可以在进程间而不是主机间进行传输。TCP 提供了进程之间可靠地全双工的连接。

​IP 地址,一个 IPv4地址就是一个 32 位无符号整数,ipv6就是就是128无符号整数。TCP/IP 网络字节顺序(network byte order 大端字节顺序)。主机一般都是小端法,IP 地址通过点分十进制表示。

因特网域名,因特网定义了域名集合和 IP 地址集合之间的映射,这是通过 DNS(Domain Name System,域名系统)来维护的。每个主机条目都是一个域名和 IP 地址的等价类。本地环回地址:127.0.0.1,它为运行在同一台机器上的客户端和服务器提供了一种便利和可移植的方式,可以用来调试。域名和 IP 地址的映射基本是一对一的,但是也有多对一和一对多 的。

因特网连接是点对点的。一个套接字是链接的一个端点,每个套接字都有相应的套接字地址,用"地址:端口"表示。临时端口:客户端发起请求时,内核自动分配;知名端口:服务器套接字端口。一个连接由它两端的套接字地址唯一确定;这一对地址叫做套接字对(socket pair)(cliaddr:cliport,servadde:servport)例如((238.2.194.242:8080),(208.216.181.15:8081))

网络中进程之间如何通信

网络进程间的通信,首要解决的问题是如何唯一标识一个进程,否则通信无从谈起!

在本地可以通过进程 PID 来唯一标识一个进程,但是在网络中这是行不通的。其实 TCP/IP 协议族已经帮我们解决了这个问题,网络层的「IP 地址」可以唯一标识网络中的主机,而传输层的「协议 + 端口」可以唯一标识主机中的应用程序(进程)。

这样利用三元组「IP 地址、协议、端口」就可以唯一标识网络的进程了,网络中的进程通信就可以利用这个标志与其它进程进行交互。

使用 TCP/IP 协议的应用程序通常采用应用编程接口——Socket,来实现网络进程之间的通信。

文件描述符

在 Linux 中,一切皆文件。一个硬件设备也可以被映射为一个虚拟的文件,称为设备文件。例如,stdin 称为标准输入文件,它对应的硬件设备一般是键盘,stdout 称为标准输出文件,它对应的硬件设备一般是显示器。

「一切皆文件」的思想极大地简化了程序员的理解和操作,使得对硬件设备的处理就像普通文件一样。所有在 Linux 中创建的文件都有一个 int 类型的编号,称为文件描述符(File Descriptor,简称 FD)。使用文件时,我们只需要知道文件描述符就可以,例如,stdin 的描述符为 0,stdout 的描述符为 1。

在Linux中,socket 也被认为是文件的一种,和普通文件的操作没有区别,所以在网络数据传输过程中自然可以使用与文件 I/O 相关的函数。可以认为,两台计算机之间的通信,实际上是两个 socket 文件的相互读写。

文件描述符有时也被称为文件句柄(File Handle),但「句柄」主要是 Windows 中术语。

socket interface(套接字接口)、

socket :的作用是创建一个套接字描述符。connect :与指定地址和端口的服务器建立连接 。bind :将套接字描述符和服务器套接字地址联系起来(即和自己的 IP 等信息)。listen:服务器调用告诉内核,这是一个主动套接字并使用主动连接描述符(被服务器使用)。accept:返回给客户端一个已连接描述符,使用已连接描述符客户端可以和服务器端进行通信。