0%

计算机网络大赏

计算机网络面经,极简共22个问题。

[1] 参考了cyc2018的总结(偏理解)

[2] 参考了JavaGuide的一些总结]

[3] 参考了公众号程序员库森的面经总结

1. 计算机网络的各层协议及作用?

计算机网络体系可以大致分为一下三种,OSI七层模型、TCP/IP四层模型和五层模型。

五层网络体系结构各层的主要功能:

  • 应用层:通过不同主机上应用进程之间的交互来完成特定的网络功能,例如 HTTP、DNS 等协议。数据单位为报文。
  • 运输层:负责为两台主机进程之间的通信提供通用的数据传输服务。运输层主要有两种协议:
    • TCP:提供面向连接的、可靠的数据传输服务;数据单位为报文段
    • UDP:提供无连接的、尽最大努力的数据传输服务,但不保证数据传输的可靠性。数据单位为用户数据报
  • 网络层:选择合适的路由和交换结点,确保数据及时传送。网络层把传输层传递下来的报文段或者用户数据报封装成分组进行传输。主要包括IP协议。
  • 数据链路层:将网络层传下来的IP分组封装成帧,并再相邻节点的链路上传送帧。
  • 物理层:实现相邻节点间比特流的透明传输,尽可能屏蔽传输介质和通信手段的差异,使数据链路层感觉不到这些差异。

图片

2. TCP和UDP的区别?

TCP\UDP都是传输层的协议,TCP指传输控制协议,UDP指用户数据报协议

  • TCP 保证数据的可靠传输,UDP 只尽最大努力交付,即不保证可靠交付。

  • TCP 是面向连接的,而 UDP 是无连接的,发送数据之前不需要建立连接,减少了开销和发送数据之前 的时延。

  • TCP 是面向字节流的,UDP 是面向报文的。UDP 对应用层交下来的报文既不拆分也不合并,传输整个报文。当报文过短或过长都会影响网络层的传输效率。

  • TCP 有拥塞控制,UDP 没有拥塞控制,因此网络中出现的拥塞不会降低源主机的发送速率。

  • TCP 是点到点之间的一对一通信,UDP 支持一对一、一对多和多对多的交互通信。

  • UDP 的首部开销很小,只有 8 字节,TCP 的首部开销为20个字节。

适应场景的区别:

  • TCP:适应用于传输效率要求较低,但准确率要求较高的场景,例如:文件传输、接收邮件、HTTP。
  • UDP:适用于效率要求相对较高,但准确性相对较低的场景, 例如:QQ聊天、在线视频、语音电话、DNS等

3. 详细介绍一下 TCP 的三次握手机制?

image-20210616092718682
  • SYN同步字段:用来建立连接,需要消耗一个序号;ACK确认字段:是确认报文段的标识,确认报文须设置ACK为1。
  • 假设A是客户端,B是服务器;初始都是CLOSED状态,B会先创建一个连接控制块TCB并进入LISTEND收听状态,监听端口是否收到了连接请求、以便及时响应
  • 第一次握手:A主动打开,发送建立连接的请求报文、其中SYN同步字段=1,并且消耗一个序号;假设A此时的发送序号为x。发送完之后A处于SYN_SENT同步已发送的状态;
  • 第二次握手:B收到A发送过来的请求连接的报文,发送给A一个确认收到的报文。其中SYN同步字段=1,ACK确认字段=1;假设此时B的发送序号为y,确认号为x+1。发送完之后B处于SYN_RCVD同步已收到的状态;
  • 第三次握手:A收到B的确认报文之后,还要给B发送一个确认报文。其中ACK确认字段=1;发送序号为x+1,确认号为y+1;发送完之后A处于连接已建立的状态;当B收到这个确认报文后、也进入连接已建立的状态。服务器要比客户端稍晚一点进入已连接的状态

4. 为什么需要三次握手,而不是两次?

三次握手的两个主要原因:信息对等和防止超时

  • 信息对等指客服端服务器都需要确认自己和对方有接受和发送报文段的能力。如果只有两次握手,那么站在服务器的角度、就不确定对方是否有接受报文段的能力。
  • 三次握手也防止失效连接突然到达导致脏连接。客服端的某个超时连接突然到达,服务器以为A发送了连接请求,就发送确认报文,建立连接。如果是两报文握手连接就建立了、浪费了资源。。三报文握手A收到确认报文时并非处于同步已发送状态,所以并不会向B发送确认报文,不会建立连接。

5. 三次握手连接阶段,最后一次ACK包丢失,会发生什么?

服务端:

  • 第三次的ACK在网络中丢失,那么服务端该TCP连接的状态为同步已收到SYN_RECV,并且会根据 TCP的超时重传机制,会等待3秒、6秒、12秒后重新发送对A的确认报文(SYN+ACK包),以便客户端重新发送第三次握手的确认报文(ACK包)。
  • 如果重发指定次数之后,仍然未收到 客户端的ACK应答,那么一段时间后,服务端自动关闭这个连接。

客户端:

客户端认为这个连接已经建立,如果客户端向服务端发送数据,服务端将以RST包(Reset,标示复位,用于异常的关闭连接)响应。此时,客户端知道第三次握手失败。

6. 详细介绍一下 TCP 的四次挥手机制?

image-20210616102556722

  • FIN指终止字段,释放连接时用来同步序号、需要消耗一个序号
  • 第一次挥手:当A已经没有要发送的数据就会释放连接,A发送一个请求终止连接的报文,其中FIN终止字段=1,发送序号假设等于x;x等于A发送的上一个报文的序号+1;发送完毕后A进入终止等待1状态。
  • 第二次挥手:当B收到A的终止连接报文后,向A发送一个确认报文,其中ACK确认字段=1,发送序号假设为y,确认序号为x+1;发送完毕后B进入关闭等待的状态,A收到确认报文后就进入终止等待2的状态。。。此时整个连接处于半关闭状态,B向上通知应用层结束A到B的连接。
  • 第三次挥手:当B的数据发送完毕后准备释放连接,就向A发送终止连接报文,其中FIN终止字段=1,发送序号设为z,此时z=y+n,n表示这个期间B发送的字节数。。确认号为x+1;发送完之后B进入最后确认阶段。
  • 第四次挥手:当A收到B的终止报文后,再向B发送一个确认报文,其中确认字段ACK=1,发送序号=x+1,确认号为z+1;发送完之后,A进入时间等待状态,等2MSL(最大报文寿命)之后进入关闭状态;B收到确认后,进入关闭状态。一般服务器先于客服端关闭。

7. 为什么客户端的 TIME-WAIT 状态必须等待 2MSL ?

  • 1、保证A的最后一个确认报文能够到达B,然后B能够正常关闭。如果该确认报文丢失,B这边没有收到就会超时重传一次终止连接的报文,重传的报文能够在2MSL时间内到达A,然后A就可以重传确认关闭的报文了。
  • 2、2MSL时间之后本连接所有的报文都会消失,可以防止已失效的连接请求与正常的连接请求相混淆。

8. 如果已经建立了连接,但是客户端出现故障了怎么办?

或者说,如果三次握手阶段、四次挥手阶段的包丢失了怎么办?如“服务端重发 FIN丢失”的问题。

简而言之,通过定时器 + 超时重试机制,尝试获取确认,直到最后会自动断开连接。

保活计时器:使客服端挂掉之后,服务器端能够主动终止连接

  • 服务器每收到一次客户端的数据就重置保活器为两小时,如果两小时内没有收到就每间隔75秒发送一次探测报文,连续发10次客服端还没响应,就关闭连接。

9 TCP流量控制

  • 利用滑动窗口实现流量控制,即让发送方的速率不要太快、以便接收方能够来得及接收
  • 主要流程:接受方的确认字段含 reverse Windows 大小的信息:”rwnd=x”,并确认字段要带ACK=1标识
  • 如果确认字段rwnd=x丢失,可能会出现相互等待的死锁情况。为此设置一个持续计时器、按时发送零窗口探测报文。

10 TCP拥塞控制

拥塞指对资源的需求大于可用的资源,,拥塞是一个全局动态的过程、仅仅增加资源可能并不会解决拥塞。

通过拥塞窗口(是一个变量)控制:发送方一般让自己的发送窗口的大小等于拥塞窗口的大小。然后动态修改之,当没有出现拥塞时,就增大拥塞窗口;当可能出现拥塞时,就缩减拥塞窗口值;

拥塞控制的算法:

  • 1慢开始算法
    • 由小逐渐间增大拥塞窗口cwnd的值,每经过一个传输轮次、窗口值就加倍。。为防止指数增长、设置一个慢开始门限ssthresh,当cwnd值大于门限时,启用拥塞避免算法。
  • 2拥塞避免算法
    • cwnd以线性规律增长
  • 3快重传算法
    • 接收方只要发现有缺失,无论下一个接受到的是什么报文段,总是立即返回丢失报文的上一个报文段的确认。
    • 一旦发送方收到三个重复的确认,就能尽早的知道发生了失序。然后立刻重传(那个重复确认报文段的)下一个报文段
  • 4快恢复算法
    • 当仅丢失个别失序报文段时,启动快速重传、、此时重传没必要从最开始的慢开始算法启动,而是直接执行拥塞避免算法,即调整慢开始门限值和当前拥塞窗口值为原先拥塞窗口的一半,直接启动拥塞避免算法。

11 TCP可靠传输

TCP打包传输过程:

  • 报文被分割成 TCP 认为最适合发送的报文段,然后把每个报文段打包传输。
  • TCP 给发送的每一个包进行编号,接收方对数据包进行排序,把有序数据传送给应用层。
  • 检验和:通过检验和的方式,接收端可以检测出来数据是否有差错和异常,假如有差错就会直接丢弃TCP段,重新发送。
  • 序列号/确认应答:序列号的作用不仅仅是应答的作用,有了序列号能够将接收到的数据根据序列号排序,并且去掉重复序列号的数据。

TCP的两个重传协议:

  • 超时重传协议:超时重传是指发送出去的数据包到接收到确认包之间的时间,如果超过了这个时间会被认为是丢包了,需要重传。最大超时时间是动态计算的
  • 连续ARQ(自动重传请求)协议:
    • 发送方维持一个发送窗口、窗口内的分组都可以连续发送出去,而不必等待确认重传;
    • 如果窗口按序收到了一个“确认”、窗口就向后滑动一格
    • 这里的确认机制指累计确认方式、接收方对按序收到的最后一个分组发送确认,确认一旦接受、就认为这个分组之前的确认都收到了

12 浏览器输入url地址,到显示页面的过程

  • 1 DNS解析:实现了网址到IP地址的转换

    • 浏览器搜索自己的DNS缓存(维护一张域名与IP的对应表);若没有,则搜索操作系统的DNS缓存(维护一张域名与IP的对应表);若没有,则搜索操作系统的hosts文件(维护一张域名与IP的对应表)。

    • 若都没有,则找 tcp/ip 参数中设置的首选 dns 服务器,即本地 dns 服务器(递归查询),本地域名服务器查询自己的dns缓存,如果没有,则进行迭代查询。将本地dns服务器将IP返回给操作系统,同时缓存IP。

  • 2 TCP连接:发起 tcp 的三次握手,建立 tcp 连接。浏览器会以一个随机端口(1024-65535)向服务端的 web 程序 80 端口发起 tcp 的连接。

  • 3 建立 tcp 连接后客户端发起 http 请求

  • 4 服务器处理请求并返回HTTP报文

    • 服务器 web 应用程序收到 http 请求后,就开始处理请求,处理之后就返回给浏览器 html 文件。
  • 5 浏览器解析解析 html 代码,并对页面进行渲染,呈现给用户。

  • 6 连接结束

20210616124706

13 介绍一下HTTP协议

HTTP 即超文本传输协议,是 Web 的应用层协议。HTTP定义了浏览器怎样向万维网服务器请求文档、以及服务器怎样把文档传输给浏览器

HTTP在运输层使用TCP协议,TCP 为 HTTP 提供可靠的数据传输服务。

HTTP 是一种无状态的协议,打开一个服务器上的网页和你之前打开这个服务器上的网页之间没有任何区别。一般靠cookie和session来保存状态

14 HTTP常见的状态码有哪些?

常见状态码:

  • 200:服务器已成功处理了请求。通常,这表示服务器提供了请求的网页。
  • 301 :(永久移动) 请求的网页已永久移动到新位置。服务器返回此响应(对 GET 或 HEAD 请求的响应)时,会自动将请求者转到新位置。
  • 302:(临时移动) 服务器目前从不同位置的网页响应请求,但请求者应继续使用原有位置来进行以后的请求。
  • 400 :客户端请求有语法错误,不能被服务器所理解。
  • 403 :服务器收到请求,但是拒绝提供服务。
  • 404 :(未找到) 服务器找不到请求的网页。
  • 500:(服务器内部错误) 服务器遇到错误,无法完成请求。

状态码开头代表类型:

图片

15 HTTP 常用的请求方式?

方法 作用
GET 获取资源
POST 传输实体主体
PUT 上传文件
DELETE 删除文件
HEAD 和GET方法类似,但只返回报文首部,不返回报文实体主体部分
PATCH 对资源进行部分修改
OPTIONS 查询指定的URL支持的方法
CONNECT 要求用隧道协议连接代理
TRACE 服务器会将通信路径返回给客户端

为了方便记忆,可以将PUT、DELETE、POST、GET理解为客户端对服务端的增删改查。

  • PUT:上传文件,向服务器添加数据,可以看作增。
  • DELETE:删除文件。
  • POST:传输数据,向服务器提交数据,对服务器数据进行更新。
  • GET:获取资源,查询服务器资源。

16 post和get区别

  • GET 用于获取资源,而 POST 用于传输实体主体。
  • GET 的参数是以查询字符串出现在 URL 中,而 POST 的参数存储在实体主体中。
    • 因此GET 只支持 ASCII 码,且参数长度有限制<2kb
    • POST 参数支持标准字符集多种编码方式。
  • GET和POST本质上就是TCP链接,并无差别。
  • GET请求会被浏览器主动缓存,GET在浏览器回退/刷新时是无害的,而POST会再次提交请求。

17 HTTP请求报文和响应报文的格式?

请求报文格式

  1. 请求行(请求方法+URI协议+版本)
  2. 请求头部(具体几个参数还要看一看)
  3. 空行
  4. 请求主体
1
2
3
4
5
6
7
8
9
10
GET/sample.jspHTTP/1.1 请求行
Accept:image/gif.image/jpeg, 浏览器可以接收的内容类型
Accept-Language:zh-cn 浏览器接收的语言
Connection:Keep-Alive 是否开启长连接
Host:localhost 被服务器的域名或IP地址,如果不是通用端口,还包含该端口号
User-Agent:Mozila/4.0(compatible;MSIE5.01;Window NT5.0)
Accept-Encoding:gzip,deflate 浏览器可以处理的编码方式
//还可以有cookie等...

username=jinqiao&password=1234 请求主体

响应报文

  1. 状态行(版本+状态码+原因短语)
  2. 响应首部
  3. 空行
  4. 响应主体
1
2
3
4
5
6
7
8
9
10
11
12
13
HTTP/1.1 200 OK
Server:Apache Tomcat/5.0.12
Date:Mon,6Oct2003 13:23:42 GMT
Content-Length:112

<html>
<head>
<title>HTTP响应示例<title>
</head>
<body>
Hello HTTP!
</body>
</html>

18 解释一下HTTP长连接和短连接?

HTTP协议的长连接和短连接,实质上是TCP协议的长连接和短连接。

在HTTP/1.0中,默认使用的是短连接。也就是说,浏览器和服务器每进行一次HTTP操作,就建立一次连接,但任务结束就中断连接。如果客户端浏览器访问的某个HTML或其他类型的 Web页中包含有其他的Web资源,如JavaScript文件、图像文件、CSS文件等;当浏览器每遇到这样一个Web资源,就会建立一个HTTP会话。

但从 HTTP/1.1起,默认使用长连接,用以保持连接特性。使用长连接的HTTP协议,会在响应头有加入这行代码:Connection:keep-alive

在使用长连接的情况下,当一个网页打开完成后,客户端和服务器之间用于传输HTTP数据的 TCP连接不会关闭,如果客户端再次访问这个服务器上的网页,会继续使用这一条已经建立的连接。Keep-Alive不会永久保持连接,它有一个保持时间,可以在不同的服务器软件(如Apache)中设定这个时间。实现长连接要客户端和服务端都支持长连接。

19 http和https的区别

  • 端口 :HTTP默认使用端口80,而HTTPS使用端口443。
  • 安全性和资源消耗:HTTP 安全性没有 HTTPS高,但是 HTTP 比HTTPS耗费的服务器资源更少。
    • HTTP协议运行在TCP之上,所有传输的内容都是明文,客户端和服务器端都无法验证对方的身份。
    • HTTPS所有传输的内容都经过加密,加密采用对称加密,但对称加密的密钥用服务器方的证书进行了非对称加密。
      • 对称加密:密钥只有一个,加密解密为同一个密码,且加解密速度快,典型的对称加密算法有DES、AES等;
      • 非对称加密:密钥成对出现(且根据公钥无法推知私钥,根据私钥也无法推知公钥),加密解密使用不同密钥(公钥加密需要私钥解密,私钥加密需要公钥解密),相对对称加密速度较慢,典型的非对称加密算法有RSA、DSA等。

20 Cookie、Session的区别

Cookie通过在客户端记录信息确定用户身份

类似给客户端们颁发一个通行证吧,每人一个,无论谁访问都必须携带自己通行证。这样服务器就能从通行证上确认客户身份了。这就是Cookie的工作原理。Cookie实际上是一小段的文本信息,储存在浏览器中。服务器还可以根据需要修改Cookie的内容。

Session通过在服务器端记录信息确定用户身份

Session相当于程序在服务器上建立的一份客户档案,类似于一份“客户明细表”,客户来访的时候只需要查询客户档案表就可以了。Session会增加一些服务器端的存储压力。

cookie和session的区别

  • cookie数据存放在客户的浏览器上,session数据放在服务器上.

  • 一个是IE启动到IE关闭.(浏览器页面一关 ,session就消失了),一个是预先设置的生存周期,或永久的保存于本地的文件。(cookie)

  • session会比较占用你服务器的性能考虑到减轻服务器性能方面,应当使用cookie,考虑到安全应当使用session。

  • 单个cookie保存的数据不能超过4K,很多浏览器都限制一个站点最多保存20个cookie

21 SQL注入是什么,如何避免SQL注入?

SQL 注入就是在用户输入的字符串中加入 SQL 语句,如果在设计不良的程序中忽略了检查,那么这些注入进去的 SQL 语句就会被数据库服务器误认为是正常的 SQL 语句而运行,攻击者就可以执行计划外的命令或访问未被授权的数据。

SQL注入的原理主要有以下 4 点

  • 恶意拼接查询
  • 利用注释执行非法命令
  • 传入非法参数
  • 添加额外条件

避免SQL注入的一些方法

  • 限制数据库权限,给用户提供仅仅能够满足其工作的最低权限。
  • 对进入数据库的特殊字符(’”\尖括号&*;等)转义处理。
  • 提供参数化查询接口,不要直接使用原生SQL。
  • ${} #{}都是进行动态传参的标记符,尽量用#{}进行传参
    • ${}在动态解析SQL阶段就直接替换为一个字符串
    • #{}是先用一个占位符?占位,然后在SQL执行的时候进行变量替换
    • #{}可以避免sql注入,能用#{}的应该尽量用#{}。表名参数的传递必须用${}

22 负载均衡算法有哪些?

多台服务器以对称的方式组成一个服务器集合,每台服务器都具有等价的地位,能互相分担负载。

  • 轮询法:将请求按照顺序轮流的分配到服务器上。大锅饭,不能发挥某些高性能服务器的优势。
  • 随机法:随机获取一台,和轮询类似。
  • 哈希法:通过ip地址哈希化来确定要选择的服务器编号。好处是,每次客户端访问的服务器都是同一个服务器,能很好地利用session或者cookie。
  • 加权轮询:根据服务器性能不同加权。
-------------感谢阅读没事常来-------------