运维开发工程师面经

整理自牛客网傻妞妞-MM面经

Linux 系统

  • 基本命令(系统性能信息的各种查看命令、可能会继续向下延伸:比如实时 CPU 负载的获取、网卡流量的抓包获取等,建议有多详细整理多详细。防火墙,文件查看,各种常用命令,请参考鸟哥基础等等。);
  • 开机启动过程,run level 各个级别的意思;
  • 文件系统区别;
  • shell 脚本对于日志文件获取有用信息的处理;
  • shell 中常使用参数的意义;
  • Awk、sed 等工具的使用;
  • 软链接、硬链接;
  • 常见的运维相关知识;

计算机网络

TCP 和 UDP

TCP 和 UDP 的区别

  • 用户数据报协议 UDP(User Datagram Protocol)是无连接的,尽最大可能交付,没有拥塞控制,面向报文(对于应用程序传下来的报文不合并也不拆分,只是添加 UDP 首部),支持一对一、一对多、多对一和多对多的交互通信。
  • 传输控制协议 TCP(Transmission Control Protocol)是面向连接的,提供可靠交付,有流量控制,拥塞控制,提供全双工通信,面向字节流(把应用层传下来的报文看成字节流,把字节流组织成大小不等的数据块),每一条 TCP 连接只能是点对点的(一对一)。

三次握手四次挥手,以及其中各个状态的转换,为什么是三次和四次?Time_wait 等待的意义?

TCP 的三次握手


假设 A 为客户端,B 为服务器端。

  • 首先 B 处于 LISTEN(监听)状态,等待客户的连接请求。

  • A 向 B 发送连接请求报文,SYN=1,ACK=0,选择一个初始的序号 x。

  • B 收到连接请求报文,如果同意建立连接,则向 A 发送连接确认报文,SYN=1,ACK=1,确认号为 x+1,同时也选择一个初始的序号 y。

  • A 收到 B 的连接确认报文后,还要向 B 发出确认,确认号为 y+1,序号为 x+1。

  • B 收到 A 的确认后,连接建立。

三次握手的原因

第三次握手是为了防止失效的连接请求到达服务器,让服务器错误打开连接。

客户端发送的连接请求如果在网络中滞留,那么就会隔很长一段时间才能收到服务器端发回的连接确认。客户端等待一个超时重传时间之后,就会重新请求连接。但是这个滞留的连接请求最后还是会到达服务器,如果不进行三次握手,那么服务器就会打开两个连接。如果有第三次握手,客户端会忽略服务器之后发送的对滞留连接请求的连接确认,不进行第三次握手,因此就不会再次打开连接。

TCP 的四次挥手


以下描述不讨论序号和确认号,因为序号和确认号的规则比较简单。并且不讨论 ACK,因为 ACK 在连接建立之后都为 1。

  • A 发送连接释放报文,FIN=1。

  • B 收到之后发出确认,此时 TCP 属于半关闭状态,B 能向 A 发送数据但是 A 不能向 B 发送数据。

  • 当 B 不再需要连接时,发送连接释放报文,FIN=1。

  • A 收到后发出确认,进入 TIME-WAIT 状态,等待 2 MSL(最大报文存活时间)后释放连接。

  • B 收到 A 的确认后释放连接。

四次挥手的原因

客户端发送了 FIN 连接释放报文之后,服务器收到了这个报文,就进入了 CLOSE-WAIT 状态。这个状态是为了让服务器端发送还未传送完毕的数据,传送完毕之后,服务器会发送 FIN 连接释放报文。

TIME_WAIT

客户端接收到服务器端的 FIN 报文后进入此状态,此时并不是直接进入 CLOSED 状态,还需要等待一个时间计时器设置的时间 2MSL。这么做有两个理由:

  • 确保最后一个确认报文能够到达。如果 B 没收到 A 发送来的确认报文,那么就会重新发送连接释放请求报文,A 等待一段时间就是为了处理这种情况的发生。

  • 等待一段时间是为了让本连接持续时间内所产生的所有报文都从网络中消失,使得下一个新的连接不会出现旧的连接请求报文。

TCP 保证可靠的传输机制

TCP 使用超时重传来实现可靠传输:如果一个已经发送的报文段在超时时间内没有收到确认,那么就重传这个报文段。

TCP 滑动窗口和回退 N 帧协议

TCP 滑动窗口

窗口是缓存的一部分,用来暂时存放字节流。发送方和接收方各有一个窗口,接收方通过 TCP 报文段中的窗口字段告诉发送方自己的窗口大小,发送方根据这个值和其它信息设置自己的窗口大小。

发送窗口内的字节都允许被发送,接收窗口内的字节都允许被接收。如果发送窗口左部的字节已经发送并且收到了确认,那么就将发送窗口向右滑动一定距离,直到左部第一个字节不是已发送并且已确认的状态;接收窗口的滑动类似,接收窗口左部字节已经发送确认并交付主机,就向右滑动接收窗口。

接收窗口只会对窗口内最后一个按序到达的字节进行确认,例如接收窗口已经收到的字节为 {31, 34, 35},其中 {31} 按序到达,而 {34, 35} 就不是,因此只对字节 31 进行确认。发送方得到一个字节的确认之后,就知道这个字节之前的所有字节都已经被接收。


回退 N 帧协议

当有错误帧出现后,总是要重发该帧之后的所有帧

TCP 的流量控制

流量控制是为了控制发送方发送速率,保证接收方来得及接收。

接收方发送的确认报文中的窗口字段可以用来控制发送方窗口大小,从而影响发送方的发送速率。将窗口字段设置为 0,则发送方不能发送数据。

TCP 的拥塞控制,拥塞控制中的四个算法

如果网络出现拥塞,分组将会丢失,此时发送方会继续重传,从而导致网络拥塞程度更高。因此当出现拥塞时,应当控制发送方的速率。这一点和流量控制很像,但是出发点不同。流量控制是为了让接收方能来得及接收,而拥塞控制是为了降低整个网络的拥塞程度。


TCP 主要通过四种算法来进行拥塞控制:慢开始、拥塞避免、快重传、快恢复。



SYN 攻击以及解决办法

SYN 攻击原理

SYN攻击属于DOS攻击的一种,它利用TCP协议缺陷,通过发送大量的半连接请求,耗费CPU和内存资源。SYN攻击除了能影响主机外,还可以危害路由器、防火墙等网络系统,事实上SYN攻击并不管目标是什么系统,只要这些系统打开TCP服务就可以实施。

服务器接收到连接请求(syn=j),将此信息加入未连接队列,并发送请求包给客户(syn=k,ack=j+1),此时进入SYN_RECV状态。当服务器未收到客户端的确认包时,重发请求包,一直到超时,才将此条目从未连接队列删除。配合IP欺骗,SYN攻击能达到很好的效果,通常,客户端在短时间内伪造大量不存在的IP地址,向服务器不断地发送syn包,服务器回复确认包,并等待客户的确认,由于源地址是不存在的,服务器需要不断的重发直至超时,这些伪造的SYN包将长时间占用未连接队列,正常的SYN请求被丢弃,目标系统运行缓慢,严重者引起网络堵塞甚至系统瘫痪。

SYN 攻击防范技术

主要有两大类,一类是通过防火墙、路由器等过滤网关防护,另一类是通过加固 TCP/IP 协议栈防范。但必须清楚的是,SYN 攻击不能完全被阻止,我们所做的是尽可能的减轻 SYN 攻击的危害,除非将 TCP 协议重新设计。

  1. 过滤网关防护

这里,过滤网关主要指明防火墙,当然路由器也能成为过滤网关。防火墙部署在不同网络之间,防范外来非法攻击和防止保密信息外泄,它处于客户端和服务器之间,利用它来防护 SYN 攻击能起到很好的效果。过滤网关防护主要包括超时设置,SYN 网关和 SYN 代理三种。

  • 网关超时设置:防火墙设置 SYN 转发超时参数(状态检测的防火墙可在状态表里面设置),该参数远小于服务器的 timeout 时间。当客户端发送完 SYN 包,服务端发送确认包后(SYN+ACK),防火墙如果在计数器到期时还未收到客户端的确认包(ACK),则往服务器发送 RST 包,以使服务器从队列中删去该半连接。值得注意的是,网关超时参数设置不宜过小也不宜过大,超时参数设置过小会影响正常的通讯,设置太大,又会影响防范 SYN 攻击的效果,必须根据所处的网络应用环境来设置此参数。
  • SYN 网关:SYN 网关收到客户端的 SYN 包时,直接转发给服务器;SYN 网关收到服务器的 SYN/ACK 包后,将该包转发给客户端,同时以客户端的名义给服务器发 ACK 确认包。此时服务器由半连接状态进入连接状态。当客户端确认包到达时,如果有数据则转发,否则丢弃。事实上,服务器除了维持半连接队列外,还要有一个连接队列,如果发生 SYN 攻击时,将使连接队列数目增加,但一般服务器所能承受的连接数量比半连接数量大得多,所以这种方法能有效地减轻对服务器的攻击。
  • SYN 代理:当客户端 SYN 包到达过滤网关时,SYN 代理并不转发 SYN 包,而是以服务器的名义主动回复SYN/ACK包给客户,如果收到客户的ACK包,表明这是正常的访问,此时防火墙向服务器发送ACK包并完成三次握手。SYN代理事实上代替了服务器去处理SYN攻击,此时要求过滤网关自身具有很强的防范SYN攻击能力。
  1. 加固 TCP/IP 协议栈

防范 SYN 攻击的另一项主要技术是调整 TCP/IP 协议栈,修改 TCP 协议实现。主要方法有 SynAttackProtect 保护机制、SYN cookies 技术、增加最大半连接和缩短超时时间等。TCP/IP 协议栈的调整可能会引起某些功能的受限,管理员应该在进行充分了解和测试的前提下进行此项工作。

  • SynAttackProtect 机制:SynAttackProtect 机制是通过关闭某些 socket 选项,增加额外的连接指示和减少超时时间,使系统能处理更多的 SYN 连接,以达到防范 SYN 攻击的目的。
  • SYN cookies 技术:我们知道,TCP 协议开辟了一个比较大的内存空间 backlog 队列来存储半连接条目,当 SYN 请求不断增加, 致使系统丢弃 SYN 连接。为使半连接队列被塞满的情况下,服务器仍能处理新到的 SYN 请求,SYN cookies技术被设计出来。

SYN cookies 应用于 linux、FreeBSD 等操作系统,当半连接队列满时,SYN cookies 并不丢弃 SYN 请求,而是通过加密技术来标识半连接状态。

在 TCP 实现中,当收到客户端的 SYN 请求时,服务器需要回复 SYN+ACK 包给客户端,客户端也要发送确认包给服务器。通常,服务器的初始序列号由服务器按照一定的规律计算得到或采用随机数,但在 SYN cookies 中,服务器的初始序列号是通过对客户端 IP 地址、客户端端囗、服务器 IP 地址和服务器端囗以及其他一些安全数值等要素进行 hash 运算,加密得到的,称之为 cookie。当服务器遭受 SYN 攻击使得 backlog 队列满时,服务器并不拒绝新的 SYN 请求,而是回复 cookie(回复包的 SYN 序列号)给客户端, 如果收到客户端的 ACK 包,服务器将客户端的ACK序列号减去1得到 cookie 比较值,并将上述要素进行一次 hash 运算,看看是否等于此 cookie。如果相等,直接完成三次握手(注意:此时并不用查看此连接是否属于 backlog 队列)。

  • 增加最大半连接数:大量的 SYN 请求导致未连接队列被塞满,使正常的 TCP 连接无法顺利完成三次握手,通过增大未连接队列空间可以缓解这种压力。当然 backlog 队列需要占用大量的内存资源,不能被无限的扩大。
  • 增加最大半连接数:大量的 SYN 请求导致未连接队列被塞满,使正常的 TCP 连接无法顺利完成三次握手,通过增大未连接队列空间可以缓解这种压力。当然 backlog 队列需要占用大量的内存资源,不能被无限的扩大。

HTTP

常见状态码

服务器返回的 响应报文 中第一行为状态行,包含了状态码以及原因短语,用来告知客户端请求的结果。

状态码 类别 原因短语
1XX Informational(信息性状态码) 接收的请求正在处理
2XX Success(成功状态码) 请求正常处理完毕
3XX Redirection(重定向状态码) 需要进行附加操作以完成请求
4XX Client Error(客户端错误状态码) 服务器无法处理请求
5XX Server Error(服务器错误状态码) 服务器处理请求出错

长连接、短连接

当浏览器访问一个包含多张图片的 HTML 页面时,除了请求访问 HTML 页面资源,还会请求图片资源。如果每进行一次 HTTP 通信就要新建一个 TCP 连接,那么开销会很大。

长连接只需要建立一次 TCP 连接就能进行多次 HTTP 通信。

  • 从 HTTP/1.1 开始默认是长连接的,如果要断开连接,需要由客户端或者服务器端提出断开,使用 Connection : close
  • 在 HTTP/1.1 之前默认是短连接的,如果需要使用长连接,则使用 Connection : Keep-Alive

Get 和 Post 的区别

(一) 作用

GET 用于获取资源,而 POST 用于传输实体主体。

(二) 参数

  • GET 和 POST 的请求都能使用额外的参数
  • GET 的参数是以查询字符串出现在 URL 中,而 POST 的参数存储在实体主体中
  • URL 只支持 ASCII 码,因此 GET 的参数中如果存在中文等字符就需要先进行编码。例如 中文 会转换为 %E4%B8%AD%E6%96%87,而空格会转换为 %20。POST 参考支持标准字符集。

(三) 安全

  • 安全的 HTTP 方法不会改变服务器状态,也就是说它只是可读的。
  • GET 方法是安全的,而 POST 却不是,因为 POST 的目的是传送实体主体内容,这个内容可能是用户上传的表单数据,上传成功之后,服务器可能把这个数据存储到数据库中,因此状态也就发生了改变。

(四) 幂等性

  • 幂等的 HTTP 方法,同样的请求被执行一次与连续执行多次的效果是一样的,服务器的状态也是一样的。换句话说就是,幂等方法不应该具有副作用(统计用途除外)。
  • 在正确实现的条件下,GET,HEAD,PUT 和 DELETE 等方法都是幂等的,而 POST 方法不是。

    DELETE /idX/delete HTTP/1.1 是幂等的,即便不同的请求接收到的状态码不一样

    1
    2
    3
    4
    > DELETE /idX/delete HTTP/1.1   -> Returns 200 if idX exists
    > DELETE /idX/delete HTTP/1.1 -> Returns 404 as it just got deleted
    > DELETE /idX/delete HTTP/1.1 -> Returns 404
    >

(五) 可缓存

如果要对响应进行缓存,需要满足以下条件:

  • 请求报文的 HTTP 方法本身是可缓存的,包括 GET 和 HEAD,但是 PUT 和 DELETE 不可缓存,POST 在多数情况下不可缓存的。
  • 响应报文的状态码是可缓存的,包括:200, 203, 204, 206, 300, 301, 404, 405, 410, 414, and 501。
  • 响应报文的 Cache-Control 首部字段没有指定不进行缓存。

(六) XMLHttpRequest

为了阐述 POST 和 GET 的另一个区别,需要先了解 XMLHttpRequest:

XMLHttpRequest 是一个 API,它为客户端提供了在客户端和服务器之间传输数据的功能。它提供了一个通过 URL 来获取数据的简单方式,并且不会使整个页面刷新。这使得网页只更新一部分页面而不会打扰到用户。XMLHttpRequest 在 AJAX 中被大量使用。

  • 在使用 XMLHttpRequest 的 POST 方法时,浏览器会先发送 Header 再发送 Data。但并不是所有浏览器会这么做,例如火狐就不会。
  • 而 GET 方法 Header 和 Data 会一起发送。

HTTP 版本的区别

  • HTTP/1.1 默认是长连接

  • HTTP/1.1 支持管线化处理

  • HTTP/1.1 支持同时打开多个 TCP 连接

  • HTTP/1.1 支持虚拟主机

  • HTTP/1.1 新增状态码 100

  • HTTP/1.1 支持分块传输编码

  • HTTP/1.1 新增缓存处理指令 max-age

HTTPS

HTTP 有以下安全性问题:

  • 使用明文进行通信,内容可能会被窃听;
  • 不验证通信方的身份,通信方的身份有可能遭遇伪装;
  • 无法证明报文的完整性,报文有可能遭篡改。

HTTPs 并不是新协议,而是让 HTTP 先和 SSL(Secure Sockets Layer)通信,再由 SSL 和 TCP 通信,也就是说 HTTPs 使用了隧道进行通信。

通过使用 SSL,HTTPs 具有了加密(防窃听)、认证(防伪装)和完整性保护(防篡改)。


加密

(一) 对称密钥加密

对称密钥加密(Symmetric-Key Encryption),加密和解密使用同一密钥。

  • 优点:运算速度快;
  • 缺点:无法安全地将密钥传输给通信方。


(二) 非对称密钥加密

非对称密钥加密,又称公开密钥加密(Public-Key Encryption),加密和解密使用不同的密钥。

公开密钥所有人都可以获得,通信发送方获得接收方的公开密钥之后,就可以使用公开密钥进行加密,接收方收到通信内容后使用私有密钥解密。

非对称密钥除了用来加密,还可以用来进行签名。因为私有密钥无法被其他人获取,因此通信发送方使用其私有密钥进行签名,通信接收方使用发送方的公开密钥对签名进行解密,就能判断这个签名是否正确。

  • 优点:可以更安全地将公开密钥传输给通信发送方;
  • 缺点:运算速度慢。


(三) HTTPs 采用的加密方式

HTTPs 采用混合的加密机制,使用非对称密钥加密用于传输对称密钥来保证传输过程的安全性,之后使用对称密钥加密进行通信来保证通信过程的效率。(下图中的 Session Key 就是对称密钥)


认证

通过使用 证书 来对通信方进行认证。

数字证书认证机构(CA,Certificate Authority)是客户端与服务器双方都可信赖的第三方机构。

服务器的运营人员向 CA 提出公开密钥的申请,CA 在判明提出申请者的身份之后,会对已申请的公开密钥做数字签名,然后分配这个已签名的公开密钥,并将该公开密钥放入公开密钥证书后绑定在一起。

进行 HTTPs 通信时,服务器会把证书发送给客户端。客户端取得其中的公开密钥之后,先使用数字签名进行验证,如果验证通过,就可以开始通信了。

通信开始时,客户端需要使用服务器的公开密钥将自己的私有密钥传输给服务器,之后再进行对称密钥加密。


完整性保护

SSL 提供报文摘要功能来进行完整性保护。

HTTP 也提供了 MD5 报文摘要功能,但不是安全的。例如报文内容被篡改之后,同时重新计算 MD5 的值,通信接收方是无法意识到发生了篡改。

HTTPs 的报文摘要功能之所以安全,是因为它结合了加密和认证这两个操作。试想一下,加密之后的报文,遭到篡改之后,也很难重新计算报文摘要,因为无法轻易获取明文。

HTTPs 的缺点

  • 因为需要进行加密解密等过程,因此速度会更慢;
  • 需要支付证书授权的高额费用。

DNS

DNS 的解析过程


  • DNS 中的字段
  • DNS 的工作原理是什么?
  • 如果 DNS 解析出现错误,怎么解决?

常见的其他问题

Ping 和 Traceroute 的工作原理

网际控制报文协议 ICMP 是为了更有效地转发 IP 数据报和提高交付成功的机会。它封装在 IP 数据报中,但是不属于高层协议。

Ping

Ping 是 ICMP 的一个重要应用,主要用来测试两台主机之间的连通性。

Ping 的原理是通过向目的主机发送 ICMP Echo 请求报文,目的主机收到之后会发送 Echo 回答报文。Ping 会根据时间和成功响应的次数估算出数据包往返时间以及丢包率。

Traceroute

Traceroute 是 ICMP 的另一个应用,用来跟踪一个分组从源点到终点的路径。

Traceroute 发送的 IP 数据报封装的是无法交付的 UDP 用户数据报,并由目的主机发送终点不可达差错报告报文。

  • 源主机向目的主机发送一连串的 IP 数据报。第一个数据报 P1 的生存时间 TTL 设置为 1,当 P1 到达路径上的第一个路由器 R1 时,R1 收下它并把 TTL 减 1,此时 TTL 等于 0,R1 就把 P1 丢弃,并向源主机发送一个 ICMP 时间超过差错报告报文;
  • 源主机接着发送第二个数据报 P2,并把 TTL 设置为 2。P2 先到达 R1,R1 收下后把 TTL 减 1 再转发给 R2,R2 收下后也把 TTL 减 1,由于此时 TTL 等于 0,R2 就丢弃 P2,并向源主机发送一个 ICMP 时间超过差错报文。
  • 不断执行这样的步骤,直到最后一个数据报刚刚到达目的主机,主机不转发数据报,也不把 TTL 值减 1。但是因为数据报封装的是无法交付的 UDP,因此目的主机要向源主机发送 ICMP 终点不可达差错报告报文。
  • 之后源主机知道了到达目的主机所经过的路由器 IP 地址以及到达每个路由器的往返时间。

路由器和交换机的区别

路由器

路由器(Router)又称网关设备(Gateway)是用于连接多个逻辑上分开的网络,所谓逻辑网络是代表一个单独的网络或者一个子网。当数据从一个子网传输到另一个子网时,可通过路由器的路由功能来完成。因此,路由器具有判断网络地址和选择IP路径的功能,它能在多网络互联环境中,建立灵活的连接,可用完全不同的数据分组和介质访问方法连接各种子网,路由器只接受源站或其他路由器的信息,属网络层的一种互联设备。

交换机

交换机工作于OSI参考模型的第二层,即数据链路层。交换机内部的CPU会在每个端口成功连接时,通过将MAC地址和端口对应,形成一张MAC表。在今后的通讯中,发往该MAC地址的数据包将仅送往其对应的端口,而不是所有的端口。因此,交换机可用于划分数据链路层广播,即冲突域;但它不能划分网络层广播,即广播域。

区别

(一) 工作所在的OSI层次不一样(根本区别,导致接下来的区别)

  • 交换机工作在 OSI模型的数据链路层,所以工作原理比较简单;
  • 路由器工作在OSI模型的网络层,具备更多的网络协议信息,所以可以做出更好的数据转发策略。

(二) 数据转发所依据的对象也不一样。

  • 交换机工作在数据链路层,所以交换机转发数据依靠的是每个物理地址(MAC地址),MAC地址一般是设备生产商在设备出厂时固定在设备中的,不能进行更改。
  • 路由器工作在网络层,所以其交换数据依靠网络地址(IP地址),而IP地址是由网络管理员自己分配或者系统自动获取的。

(三) 是否可以分割广播域

  • 由交换机连接的所有端口仍然属于同一个广播域,所以极有可能会产生数据拥堵;
  • 连接到路由器上的所有端口不在属于同一个广播域,所以不会产生类似的数据拥堵问题。

输入网址后,背后发生了什么?

  1. 浏览器发起 DNS 查询请求
  2. 域名服务器向客户端返回查询结果域名,从而完成域名到 IP 地址的转换。
  3. 客户端向 web 服务器发送 HTTP 请求
  4. web 服务器发送响应数据给客户端

I/O 模型以及同步异步阻塞非阻塞的区别

I/O 模型
一个输入操作通常包括两个阶段:

  • 等待数据准备好
  • 从内核向进程复制数据

对于一个套接字上的输入操作,第一步通常涉及等待数据从网络中到达。当所等待分组到达时,它被复制到内核中的某个缓冲区。第二步就是把数据从内核缓冲区复制到应用进程缓冲区。

Unix 下有五种 I/O 模型:

  • 阻塞式 I/O
  • 非阻塞式 I/O
  • I/O 复用(select 和 poll)
  • 信号驱动式 I/O(SIGIO)
  • 异步 I/O(AIO)

阻塞式 I/O

应用进程被阻塞,直到数据复制到应用进程缓冲区中才返回。

应该注意到,在阻塞的过程中,其它程序还可以执行,因此阻塞不意味着整个操作系统都被阻塞。因为其他程序还可以执行,因此不消耗 CPU 时间,这种模型的执行效率会比较高。


非阻塞式 I/O

应用进程执行系统调用之后,内核返回一个错误码。应用进程可以继续执行,但是需要不断的执行系统调用来获知 I/O 是否完成,这种方式称为轮询(polling)。

由于 CPU 要处理更多的系统调用,因此这种模型是比较低效的。


同步 I/O 与异步 I/O

  • 同步 I/O:应用进程在调用 recvfrom 操作时会阻塞。
  • 异步 I/O:不会阻塞。
    阻塞式 I/O、非阻塞式 I/O、I/O 复用和信号驱动 I/O 都是同步 I/O,虽然非阻塞式 I/O 和信号驱动 I/O 在等待数据阶段不会阻塞,但是在之后的将数据从内核复制到应用进程这个操作会阻塞。

B/S和C/S的区别

Client/Server 是建立在局域网的基础上的。Browser/Server 是建立在广域网的基础上的,但并不是说B/S结构不能在局域网上使用,如智赢 IPOWER,在单机,局限网,广域网均能使用。

1.硬件环境不同:

  • C/S 一般建立在专用的网络上, 小范围里的网络环境, 局域网之间再通过专门服务器提供连接和数据交换服务.
  • B/S 建立在广域网之上的, 不必是专门的网络硬件环境,例与电话上网, 租用设备. 信息自己管理. 有比C/S更强的适应范围, 一般只要有操作系统和浏览器就行

2.对安全要求不同

  • C/S 对服务端、客户端都安全都要考虑。
  • B/S 因没有客户端,所以只注重服务端安全即可。

3.对程序架构不同

  • C/S 程序可以更加注重流程, 可以对权限多层次校验, 对系统运行速度可以较少考虑.
  • B/S 对安全以及访问速度的多重的考虑, 建立在需要更加优化的基础之上. 比C/S有更高的要求 B/S结构的程序架构是发展的趋势, 从MS的.Net系列的BizTalk 2000 Exchange 2000 等, 全面支持网络的构件搭建的系统. SUN 和IBM推的JavaBean 构件技术等,使 B/S更加成熟. 例如智赢IPOWER,采用AJAX和数据存储优化技术,相比一般B/S架构软件速度提高 30%至99%。

4.软件重用不同

  • C/S 程序可以不可避免的整体性考虑, 构件的重用性不如在B/S要求下的构件的重用性好.
  • B/S 对的多重结构,要求构件相对独立的功能. 能够相对较好的重用.就入买来的餐桌可以再利用,而不是做在墙上的石头桌子

5.系统维护不同

  • C/S 程序由于整体性, 必须整体考察, 处理出现的问题以及系统升级. 升级难. 可能是再做一个全新的系统
  • B/S 构件组成,方面构件个别的更换,实现系统的无缝升级. 系统维护开销减到最小.用户从网上自己下载安装就可以实现升级.

6.处理问题不同

  • C/S 程序可以处理用户面固定, 并且在相同区域, 安全要求高需求, 与操作系统相关. 应该都是相同的系统
  • B/S 建立在广域网上, 面向不同的用户群, 分散地域, 这是C/S无法作到的. 与操作系统平台关系最小.

7.用户接口不同

  • C/S 多是建立的Window平台上,表现方法有限,对程序员普遍要求较高
  • B/S 建立在浏览器上, 通过WEB服务或其他公共可识别描述语言可跨平台,使用更灵活。不仅可应用在Window平台上,还可应用于unix/Linux等平台。

8.信息流不同

  • C/S 程序一般是典型的中央集权的机械式处理, 交互性相对低
  • B/S 信息流向可变化, B-B B-C B-G等信息、流向的变化, 更象交易中心。

  1. 路由协议OSPF、BGP的区别(这个一般很少问,除非你说你懂网络协议)

操作系统

进程和线程的区别

进程是资源分配的基本单位,线程是独立调度的基本单位。
(一)拥有资源
进程是资源分配的基本单位,但是线程不拥有资源,线程可以访问隶属进程的资源。

(二)调度
线程是独立调度的基本单位,在同一进程中,线程的切换不会引起进程切换,从一个进程内的线程切换到另一个进程中的线程时,会引起进程切换。

(三)系统开销
由于创建或撤销进程时,系统都要为之分配或回收资源,如内存空间、I/O 设备等,所付出的开销远大于创建或撤销线程时的开销。类似地,在进行进程切换时,涉及当前执行进程 CPU 环境的保存及新调度进程 CPU 环境的设置,而线程切换时只需保存和设置少量寄存器内容,开销很小。

(四)通信方面
进程间通信 (IPC) 需要进程同步和互斥手段的辅助,以保证数据的一致性。而线程间可以通过直接读/写同一进程中的数据段(如全局变量)来进行通信。

进程的状态?进程的切换方式?


  • 就绪状态(ready):等待被调度
  • 运行状态(running)
  • 阻塞状态(waiting):等待资源

应该注意以下内容:

  • 只有就绪态和运行态可以相互转换,其它的都是单向转换。就绪状态的进程通过调度算法从而获得 CPU 时间,转为运行状态;而运行状态的进程,在分配给它的 CPU 时间片用完之后就会转为就绪状态,等待下一次调度。
  • 阻塞状态是缺少需要的资源从而由运行状态转换而来,但是该资源不包括 CPU 时间,缺少 CPU 时间会从运行态转换为就绪态。

进程同步的方式有哪些

  • 信号量
  • 管程

进程的通信方式有哪些

  • 管道
  • FIFO
  • 消息队列
  • 信号量
  • 共享存储
  • 套接字

操作系统的常见进程调度算法

不同环境的调度算法目标不同,因此需要针对不同环境来讨论调度算法。

批处理系统
批处理系统没有太多的用户操作,在该系统中,调度算法目标是保证吞吐量和周转时间(从提交到终止的时间)。

  • 先来先服务 first-come first-serverd(FCFS)
  • 短作业优先 shortest job first(SJF)
  • 最短剩余时间优先 shortest remaining time next(SRTN)

交互式系统
交互式系统有大量的用户交互操作,在该系统中调度算法的目标是快速地进行响应。

  • 时间片轮转
  • 优先级调度
  • 多级反馈队列

死锁的四个条件,解决与避免的方法

死锁的四个条件

  • 互斥:每个资源要么已经分配给了一个进程,要么就是可用的。
  • 占有和等待:已经得到了某个资源的进程可以再请求新的资源。
  • 不可抢占:已经分配给一个进程的资源不能强制性地被抢占,它只能被占有它的进程显式地释放。
  • 环路等待:有两个或者两个以上的进程组成一条环路,该环路中的每个进程都在等待下一个进程所占有的资源。

办法

  • 鸵鸟策略
  • 死锁检测与死锁恢复
  • 死锁预防
  • 死锁避免

分页和分段有什么区别

  • 虚拟内存采用的是分页技术,也就是将地址空间划分成固定大小的页,每一页再与内存进行映射。
  • 分段的做法是把每个表分成段,一个段构成一个独立的地址空间。每个段的长度可以不同,并且可以动态增长。
  • 段页式:程序的地址空间划分成多个拥有独立地址空间的段,每个段上的地址空间划分成大小相同的页。这样既拥有分段系统的共享和保护,又拥有分页系统的虚拟内存功能。

分页与分段的比较

  • 对程序员的透明性:分页透明,但是分段需要程序员显示划分每个段。
  • 地址空间的维度:分页是一维地址空间,分段是二维的。
  • 大小是否可以改变:页的大小不可变,段的大小可以动态改变。
  • 出现的原因:分页主要用于实现虚拟内存,从而获得更大的地址空间;分段主要是为了使程序和数据可以被划分为逻辑上独立的地址空间并且有助于共享和保护。

  1. 数据从内存写到磁盘上发生的过程,具体行为是什么?

数据库

事务

事务指的是满足 ACID 特性的一组操作,可以通过 Commit 提交一个事务,也可以使用 Rollback 进行回滚。

ACID性质,其中各个性质的含义

  1. 原子性(Atomicity)

事务被视为不可分割的最小单元,事务的所有操作要么全部提交成功,要么全部失败回滚。

回滚可以用日志来实现,日志记录着事务所执行的修改操作,在回滚时反向执行这些修改操作即可。

  1. 一致性(Consistency)

数据库在事务执行前后都保持一致性状态。在一致性状态下,所有事务对一个数据的读取结果都是相同的。

  1. 隔离性(Isolation)

一个事务所做的修改在最终提交以前,对其它事务是不可见的。

  1. 持久性(Durability)

一旦事务提交,则其所做的修改将会永远保存到数据库中。即使系统发生崩溃,事务执行的结果也不能丢失。

可以通过数据库备份和恢复来实现,在系统发生崩溃时,使用备份的数据库进行数据恢复。

脏读、丢失修改、不可重复读、幻影读

丢失修改

$T_1$ 和 $T_2$ 两个事务都对一个数据进行修改,$T_1$ 先修改,$T_2$ 随后修改,$T_2$ 的修改覆盖了 $T_1$ 的修改。

脏读

$T_1$ 修改一个数据,$T_2$ 随后读取这个数据。如果 $T_1$ 撤销了这次修改,那么 $T_2$ 读取的数据是脏数据。

不可重复读

$T_2$ 读取一个数据,$T_1$ 对该数据做了修改。如果 $T_2$ 再次读取这个数据,此时读取的结果和第一次读取的结果不同。

幻影读

$T_1$ 读取某个范围的数据,$T_2$ 在这个范围内插入新的数据,$T_1$ 再次读取这个范围的数据,此时读取的结果和和第一次读取的结果不同。(统计求和等)

隔离级别

  • 未提交读(READ UNCOMMITTED):事务中的修改,即使没有提交,对其它事务也是可见的。
  • 提交读(READ COMMITTED):一个事务只能读取已经提交的事务所做的修改。换句话说,一个事务所做的修改在提交之前对其它事务是不可见的。
  • 可重复读(REPEATABLE READ):保证在同一个事务中多次读取同样数据的结果是一样的。
  • 可串行化(SERIALIZABLE):强制事务串行执行。
隔离级别 脏读 不可重复读 幻影读
未提交读
提交读 ×
可重复读 × ×
可串行化 × × ×

数据库的锁机制

封锁粒度

  • 行级锁
  • 表级锁

封锁类型

  • 读写锁

    • 排它锁(Exclusive),简写为 X 锁,又称写锁。
    • 共享锁(Shared),简写为 S 锁,又称读锁。
  • 意向锁:IX 、IS

封锁协议

  • 三级封锁协议

    • 一级封锁协议:事务 T 要修改数据 A 时必须加 X 锁,直到 T 结束才释放锁。可以解决丢失修改问题,因为不能同时有两个事务对同一个数据进行修改,那么事务的修改就不会被覆盖。
    • 二级封锁协议:在一级的基础上,要求读取数据 A 时必须加 S 锁,读取完马上释放 S 锁。可以解决读脏数据问题,因为如果一个事务在对数据 A 进行修改,根据 1 级封锁协议,会加 X 锁,那么就不能再加 S 锁了,也就是不会读入数据。
    • 三级封锁协议:在二级的基础上,要求读取数据 A 时必须加 S 锁,直到事务结束了才能释放 S 锁。可以解决不可重复读的问题,因为读 A 时,其它事务不能对 A 加 X 锁,从而避免了在读的期间数据发生改变。
  • 两段锁协议

    • 加锁和解锁分为两个阶段进行。
    • 可串行化调度是指,通过并发控制,使得并发执行的事务结果与某个串行执行的事务结果相同。事务遵循两段锁协议是保证可串行化调度的充分条件,但不是必要条件。

  • 常见的SQL语句(内外联结)
  • 索引、视图
  • Mysql 常见的引擎及区别
  • Mysql 的四种日志的意义
  • 数据库的备份等
  • Mysql 的优化
  • Mysql 的复制

Python

深拷贝和浅拷贝

在 python 中,对象赋值实际上是对象的引用。当创建一个对象,然后把它赋给另一个变量的时候,python 并没有拷贝这个对象,而只是拷贝了这个对象的引用。

  1. 直接赋值,传递对象的引用而已,原始列表改变,被赋值的 b 也会做相同的改变
  2. copy 浅拷贝,没有拷贝子对象,所以原始数据改变,子对象会改变
  3. deepcopy 深拷贝,包含对象里面的自对象的拷贝,所以原始对象的改变不会造成深拷贝里任何子元素的改变

  • 闭包、装饰器
  • 迭代器、生成器
  • 多线程
  • 内存管理
  • 垃圾回收机制
  • *args,**kwargs

数据结构

运维相关

高可用性、负载均衡

高可用性

计算机系统的可用性用 [1] 平均无故障时间(MTTF)来度量,即计算机系统平均能够正常运行多长时间,才发生一次故障。系统的可用性越高,平均无故障时间越长。可维护性用平均维修时间(MTTR)来度量,即系统发生故障后维修和重新恢复正常运行平均花费的时间。系统的可维护性越好,平均维修时间越短。计算机系统的可用性定义为:MTTF/(MTTF+MTTR) * 100%。由此可见,计算机系统的可用性定义为系统保持正常运行时间的百分比。

工作方式:

  1. 主从方式 (非对称方式)
    工作原理:主机工作,备机处于监控准备状况;当主机宕机时,备机接管主机的一切工作,待主机恢复正常后,按使用者的设定以自动或手动方式将服务切换到主机上运行,数据的一致性通过共享存储系统解决。

  2. 双机双工方式(互备互援)
    工作原理:两台主机同时运行各自的服务工作且相互监测情况,当任一台主机宕机时,另一台主机立即接管它的一切工作,保证工作实时,应用服务系统的关键数据存放在共享存储系统中。

  3. 集群工作方式(多服务器互备方式)
    工作原理:多台主机一起工作,各自运行一个或几个服务,各为服务定义一个或多个备用主机,当某个主机故障时,运行在其上的服务就可以被其它主机接管。

负载均衡

负载均衡可以将任务分摊到多个处理单元,从而提高并发处理能力。

(一) [协议层] HTTP 重定向协议实现负载均衡

  • 原理:根据用户的 HTTP 请求计算出一个真实的 web 服务器地址,并将该 web 服务器地址写入 HTTP 重定向响应中返回给浏览器,由浏览器重新进行访问。
  • 优点:比较简单
  • 缺点:
    • 浏览器需要两次请求服务器才能完成一次访问,性能较差。
    • HTTP 重定向服务器自身的处理能力可能成为瓶颈。
    • 使用 HTTP302 响应重定向,有可能使搜索引擎判断为 SEO 作弊,降低搜索排名。

(二) [协议层] DNS 域名解析负载均衡

  • 原理:在DNS服务器上配置多个域名对应IP的记录。例如一个域名www.baidu.com 对应一组 web 服务器 IP 地址,域名解析时经过 DNS 服务器的算法将一个域名请求分配到合适的真实服务器上。
  • 优点:将负载均衡的工作交给了 DNS,省却了网站管理维护负载均衡服务器的麻烦,同时许多 DNS 还支持基于地理位置的域名解析,将域名解析成距离用户地理最近的一个服务器地址,加快访问速度吗,改善性能。
  • 缺点:
    • 目前的 DNS 解析是多级解析,每一级DNS都可能化缓存记录A,当某一服务器下线后,该服务器对应的 DNS 记录 A 可能仍然存在,导致分配到该服务器的用户访问失败。
    • DNS负载均衡的控制权在域名服务商手里,网站可能无法做出过多的改善和管理。不能够按服务器的处理能力来分配负载。
    • DNS 负载均衡采用的是简单的轮询算法,不能区分服务器之间的差异,不能反映服务器当前运行状态,所以其的负载均衡效果并不是太好。
    • 可能会造成额外的网络问题。为了使本 DNS 服务器和其他 DNS 服务器及时交互,保证 DNS 数据及时更新,使地址能随机分配,一般都要将 DNS 的刷新时间设置的较小,但太小将会使 DNS 流量大增造成额外的网络问题。

(三) [协议层] 反向代理负载均衡

  • 原理:反向代理处于 web 服务器这边,反向代理服务器提供负载均衡的功能,同时管理一组 web 服务器,它根据负载均衡算法将请求的浏览器访问转发到不同的web 服务器处理,处理结果经过反向服务器返回给浏览器。
  • 优点:部署简单,处于 HTTP 协议层面。
  • 缺点:使用了反向代理服务器后,web 服务器地址不能直接暴露在外,因此 web服务器不需要使用外部 IP 地址,而反向代理服务作为沟通桥梁就需要配置双网卡、外部内部两套 IP 地址。

(四) [网络层] IP负载均衡

  • 原理:在网络层通过修改目标地址进行负载均衡。用户访问请求到达负载均衡服务器,负载均衡服务器在操作系统内核进程获取网络数据包,根据算法得到一台真实服务器地址,然后将用户请求的目标地址修改成该真实服务器地址,数据处理完后返回给负载均衡服务器,负载均衡服务器收到响应后将自身的地址修改成原用户访问地址后再讲数据返回回去。类似于反向服务器负载均衡。
  • 优点:在响应请求时速度较反向服务器负载均衡要快。
  • 缺点:当请求数据较大(大型视频或文件)时,速度较慢。

(五) [链路层] 数据链路层负载均衡

  • 原理:在数据链路层修改 MAC 地址进行负载均衡。负载均衡服务器的 IP 和它所管理的 web 服务群的虚拟 IP 一致;负载均衡数据分发过程中不修改访问地址的 IP 地址,而是修改 MAC 地址;通过这两点达到不修改数据包的原地址和目标地址就可以进行正常的访问。
  • 优点:不需要负载均衡服务器进行地址的转换。数据响应时不需要经过负载均衡服务器。是目前大型网站所使用得最广的一种均衡手段。
  • 缺点:负载均衡服务器的网卡带宽要求较高。

  1. Docker

  2. Nginx、lvs、keepalived、监控、cdn 等