计算机网络
TCP/IP 四层模型
》应用层
-
只需要管如何给用户提供功能和服务
-
应用层属于用户态,其他属于内核态
-
常见的应用层协议:HTTP、HTTPS、WebSocket、DNS
》传输层
-
传输层主要负责端口的分配和分发,一个设备上会有很多个应用,每个应用又会有不同的网络端口
-
常见的传输层协议:TCP、UDP
》网络层
-
网络层会将传输层的报文加上IP头组装成IP报文,然后在网络内进行传输
-
子网掩码、网关、路由、MAC 等等这些概念都属于网络层的范畴
-
常见的网络层协议:IP、ARP
》网络接口层
-
网络接口层会将数据打包成data frame发布到网络上,工作在网卡的层次
-
以太网、交换机、光纤这些概念都属于网络接口层的范畴
-
常见的网络接口层协议:Ethernet、WiFi
OSI 七层模型
访问网址全过程 ⭐
这个经典的问题,也叫从浏览器键入网址到页面展示的全过程:
-
用户在浏览器上输入URL
-
进行DNS多级寻址,找到URL对应的域名映射
-
TCP三次握手建立TCP连接
-
建立HTTP/HTTPS连接
-
如果是HTTPS还需要进行TLS握手和证书确认
-
服务端发送初始相应报文,通常是200状态码加一个index.html
-
浏览器接收文件,构建一颗HTML DOM树和一颗CSS DOM树再合并成一颗渲染树并展示给用户
Cookie \ Session \ Token
这三个概念都和状态信息息息相关,什么是状态信息?在我们完成登陆之后,如果我们希望后续所有的页面都维持登录的状态,我们就需要用到这些技术。如果没有这些技术来保存状态信息,那么每一次HTTP请求都需要进行一次登录验证,是非常低效的;
》Cookie
Cookie由服务端生成,本质上是浏览器的缓存的一部分,将信息以明文形式按照键值对存储在文本文件当中;由于Cookie有安全风险可以被篡改,而且有4KB的容量限制,用户也可以手动禁用Cookie;所以Cookie目前已经不再用来存储关键信息,而是存储一些用户偏好
》Session
Session是把用户状态信息存储到服务端的技术,在用户完成登录验证过后,服务端会创建并存储一个用户对象存入服务端的Session当中,然后返回给用户端一个session-id,以后用户只需要将session-id放置在请求头中,就可以请求到服务端Session中的信息;
Session的使用一般是结合Cookie的,在用户第一次请求服务器时,服务器创建相应的Session后会将session-id给到用户,用户会将这个session-id存储到Cookie当中,并在后续的请求中在请求头上附上session-id;
Q1: 客户端不支持Cookie怎么办?
有时候浏览器禁用Cookie,又或者是客户端是安卓IOS等等,可以使用客户端的本地缓存来替代Cookie,比如浏览器的sessionStorage
Session现在一般用用在高度依赖服务器端的状态管理时,因为这时Token里的Payload无法存入巨量的信息,比如购物车商品、浏览历史、个性化推荐等等
Q2: 分布式环境下Session怎么处理
由于现在很多服务器都是采用的分布式环境,使用Session会让会话难以管理,需要再多个服务器之间同步会话状态,如果用Session来保存所有的信息的话消耗巨量的资源;
解决方案是使用Redis等分布式缓存来存储Cookie,这样可以在多台服务器之间共享;
》Token
我们说Token其实使用的最多的就是JWT,JWT由Header、Payload、Signature三部分组成,Header中包含加密算法和Token类型,PayLoad代表存储的信息,Signature由前两部分加密形成;
在用户进行完登录校验后,客户端按照客户端的私钥和加密算法将想要存进Token的信息加密存入Payload,然后用户以后就可以将这个Token携带在请求头中访问服务端了;
Token的存在不是为了安全,而是为了缓解服务端存储的压力,因为在Token中存入数据不会消耗任何存储空间。这里可以结合项目讲讲我对JWT的具体使用;
总结: Cookie Session Token他们都是在用户访问服务器过程中用来保存状态信息的手段,分别对应不同的存储位置,用户端、服务端和存储在密钥当中。他们都是保存用户状态信息的重要手段,且有着不同的使用场景;Session可以看作是对Cookie安全性的一个升级,而Token的出现缓解了服务端Session使用的存储压力
DNS
域名和IP地址的关系可以类比姓名和手机号的关系,区别就是你只需要存储你需要的联系人和对应的手机号,但不可能要求每一台电脑都实时记录世界上所有域名和IP地址的映射关系,这样就有了DNS
-
用户输入域名,操作系统会首先检测浏览器缓存和本地的hosts有没有域名解析,没有的话
-
使用TCP\IP配置的DNS服务器进行查询,如果本地DNS服务器去查域名解析,没有的话
-
本地DNS服务器发送查询报文到根DNS服务器,拿到顶级域DNS服务器地址
-
本地DNS服务器发送查询报文到顶级域DNS服务器,拿到权威DNS服务器
-
本地DNS服务器发送查询报文到权威DNS服务器,拿到对应IP地址,完成域名解析
IP \ 子网掩码 \ NAT \ DHCP
》IPv4 和 IPv6
IPv4由4个8位2进制数组成,一共32位,而IPv6一共有128位,所以IPv4的地址数量比较少,比较紧张,现在IPv4的地址基本都被用完了,所以IPv4才会需要一些子网掩码、NAT技术来帮助分配IP地址,提高IP地址的利用率,而IPv6完全没有这样的问题,甚至可以给同一设备的不同端口设置不同的IPv6地址
》子网掩码
-
可以将当前设备的IP地址和子网掩码进行按位与得到网络ID,可以利用这个网络ID判断当前网络与目标IP地址是否存在于同一个子网当中
-
利用子网掩码可以更好的规划IP地址的分配,减少IP地址的浪费
》NAT
NAT技术说白了就是让私网下的多个设备公用一个公网IP上网,
一般集成在路由器当中,路由器会给私网下的设备分配私网IP
》DHCP
DHCP是路由器用来动态分配私网IP、自动完成网络配置的协议
可以在动态分配IP的同时,帮主机自动配置好子网掩码、网关IP、DNS服务器IP等信息
动态分配的IP一般有一个过期时间,通常是一周
CDN \ ARP \ ICMP
》CDN 内容分发网络
-
CDN是为了减少源服务器的压力,建立边缘服务器来提供服务的网络
-
一般来说,可以把一些网络静态资源部署在边缘服务器上,减少源服务器的压力
-
CDN还能提供负载均衡的功能、提供TLS\SSL加密功能、加速用户访问服务的速度
》ARP 地址解析解析
-
MAC地址和IP地址同样重要,因为如果只有IP地址,一旦IP地址被重新动态分配那么数据包就会发送错误
-
ARP协议是用来根据IP地址查找设备MAC地址的协议
-
每个设备都会存储一个IP地址和MAC地址的ARP映射表,一旦有设备更改了自己的IP地址,他就会广播ARP消息来更新其他主机的ARP映射表
》ICMP 互联网控制消息协议
ICMP(Internet Control Message Protocol,互联网控制消息协议),是Ping命令背后的协议
协议的目的是为了帮助网络管理员检测网络中发送的各种问题
TCP \ UDP ⭐
-
TCP是基于连接的协议,每次连接都需要3次握手,断开连接都需要4次挥手
-
TCP可以解决丢包问题和乱序问题;它维护了一个发送缓冲区,并且将每一个包都标记上了序列号;每次发送消息的时候,会在包头中包含当前的缓冲区的起始序列号和包长;然后接收端在接收完消息后会在ACK中返回下一段消息的起始序列号;这个环节只要有一个对不上就要进行消息重传,这样就解决了丢包问题,然后序列号的存在也解决了信息乱序的问题
-
TCP拥有流量控制功能和拥塞控制功能
三握四挥
》三次握手
-
客户端发送SYN报文
-
服务端接收返回SYN+ACK报文
-
客户端发送ACK报文
三次握手是为了确保客户端和服务端双端相互确认彼此的收发正常,所以缺一不可
服务端在步骤2中返回的是客户端的SYN报文,这样可以确保没有发错对象
》四次挥手
-
客户端发送FIN报文
-
服务端发送ACK报文
-
服务端发送FIN报文,服务端关闭连接
-
客户端发送ACK报文,等待2个MSL再关闭连接
为什么不合并服务端的ACK+FIN:服务端可能又未处理完的数据
为什么需要等待两个MSL:为了保证服务端收到了ACK报文,否则服务端会重发FIN
TCP 粘包
粘包问题的产生原因:
-
TCP协议本身具有流式传输特性,并没有消息边界,可能在传输的过程中导致粘包
-
如果接收端的缓冲区比较小,可能在接收端发送冲突导致信息被合并,导致粘包
-
如果发送端误判消息丢失使得消息重传,接收端收到两个相同的信息可能导致冲突粘包
粘包问题的解决方案:
-
发送定长包 2. 在包头写入包长 3. 在包尾加上信息边界 4.使用应用层协议
流量控制 + 拥塞控制
》流量控制
-
流量控制的目标是,发送方需要根据接收方的缓冲区来控制发送,接收方会不断地在返回给发送方的ACK报文中加入它缓冲区空闲的大小
-
如果接收端缓冲区已经满了,那么它会发送一个窗口为0的ACK报文来终止发送端的发送,然后如果接收端缓冲区重新开发窗口,他会通知发送端继续发送,但是这个报文可能丢失,为了防止死锁;发送端设置了一个定时器来对接收端进行轮询
-
除此之外,还需要解决“糊涂窗口综合症”,就是如果接收端的处理速度比较慢,每次都会发送一个很小的窗口通知发送端,这时候发送端的有效数据传输效率就会很低,因为TCP报文段头部就会占据一定数据;可以设置接收方设置一个最小窗口大小,如果窗口小于这个阈值就发送0
》拥塞控制
-
计算机网络可能由于主机的其他通信造成网络拥堵,这时候传数据就容易丢包,如果这时候没有拥塞控制,那么TCP会自动重传导致更严重地网络拥堵
-
解决的方法是在发送端维护一个拥塞窗口,发送端发送的的数据大小由接收端的窗口和拥塞窗口共同决定,取拥塞窗口和接收窗口中的最小值
-
慢启动阶段:在主机刚刚开始发送报文时先设置拥塞窗口大小为最小值,每次接收到ACK后迅速增大拥塞窗口,用于感知网络拥塞状况,慢启动拥塞窗口的增大是指数增长的
-
拥塞避免阶段:在拥塞避免阶段,拥塞窗口的增大是线性的,在每次接收到ACK后线性的增大拥塞窗口;如果丢包触发超时重传,则网络拥堵,那么会重新开启慢启动过程并设置窗口最小
TCP x SYN 泛洪攻击
SYN泛洪攻击是一种常见的DoS攻击,攻击者会伪造大量的TCP连接请求导致服务端资源耗尽,无法处理正常的连接请求;
具体来说,就是伪造大量的SYN包发送给服务端,服务端会为每个SYN包回复一个SYN-ACK包的同时,为这个未完成的连接分配一定的资源;
如何解决这种半连接服务拒绝问题:
-
SYN Cookie:收到SYN后,服务器根据一定的方法,以数据包的源地址、端口等信息为参数计算出一个Cookie值作为自己的序列号,回复后SYN+ACK后,服务端并不会分配资源给这个未完成的连接,等收到发送方的ACK后,根据源地址端口检查序列号,如果正确则建立连接;说白了就是用Cookie值代替半连接队列,这种办法会降低连接速度
-
Proxy 防火墙:用一个代理服务器来单独处理第一个SYN报文和维持半连接状态,等发送方确认ACK后,再和真正的服务器建立TCP连接
HTTP 1.0 \ 1.1 \ 2 \ 3
》HTTP 1.0
-
浏览器和服务器保持短连接,浏览器每次请求都需要重新建立TCP连接
-
队头阻塞:下一个请求必须要在前一个响应到达之前才能发送
-
不支持断点续传,每次都会传送全部的页面和数据
》HTTP 1.1
-
可以保持长连接,避免每次请求都需要建立TCP连接,提高了网络的利用率
-
可以使用管道传输,支持多个请求同时发送,但是服务器还是会按照请求顺序回应
-
支持断点续传
》HTTP 2.0
-
可以在一个TCP连接中并发多个请求和响应,彻底解决了队头阻塞问题
-
服务端不再只能被动的响应,而是可以主动向客户端推送资源
》HTTP 3.0
-
由于HTTP 2.0将HTTP连接建立在一次TCP连接上,一旦发生丢包,就会阻塞住所有的HTTP请求;
-
HTTP 3.0直接放弃使用TCP,将传输层协议改为UDP,所以HTTP 3.0引入了自己的可靠性传输协议栈QUIC,在并发环境下如果某个请求响应丢包,只会阻塞住当前线程上的请求响应,而不会阻塞整个HTTP连接;
》长连接和短连接
-
长连接就是多次HTTP请求响应都建立在一次TCP连接上
-
在建立了长连接后,服务器会通过心跳机制来管理长连接的自动断开
-
服务器的长连接数如果很多的话会比较影响性能
HTTP 请求组成
》请求头 Request Headers
-
主机名、端口号、浏览器类型、操作系统类型
-
长连接还是短连接、是否需要升级WebSocket
-
SessionID、Token
》请求行 Request Line
-
请求方法 GET、POST、PUT、DELETE
-
请求URL:用于定位资源
-
HTTP协议版本
》请求体 Request Body
实际传输的数据,表单信息,JSON数据
GET \ POST
本质区别:GET用于从服务器获取数据,POST用于向服务器提交数据
URL可见性:GET请求的参数会附加在URL的末尾,POST请求的参数会放置在请求体中
缓存性:GET请求可以被浏览器缓存,如果结果已经在缓存中存在则直接返回结果
安全性:由于GET请求参数在URL中可见,所以认为GET请求不适合用来传递敏感信息
响应状态码
1XX(信息状态码):服务器收到请求,但还需要进一步处理,一般不会返给前端
2XX(成功):200成功 201服务器已经创建资源 204客户端需要执行额外操作
3XX(重定向):301资源永久移动 302暂时移动 304重定向到用户本地缓存
4XX(请求错误): 400请求存在错误 401需要认证 403资源权限 404请求资源不存在
5XX(服务端错误):500服务端未知错误 502网关错误
HTTPS ⭐
HTTPS就是安全版的HTTP协议,具体来说在HTTP的基础上使用TLS/SSL进行加密
SSL就是TLS的前身,现在大多数浏览器都只支持TLS,不过由于SSL名气很大所以很多人都混用概念
非对称加密:如果使用对称式加密,那么一旦密钥泄漏,数据也就会被泄漏;
TLS协议采用非对称式加密,数据经过公钥加密就只能通过私钥解密,数据通过私钥加密就只能通过公钥解密;如果应用到客户端和服务端的化,服务端会持有成对的公钥和私钥,然后公布公钥让客户端知道,客户端用公钥将数据进行加密,加密后这个数据不能使用公钥解密,而是必须要用私钥才能解密,这种非对称式加密也被称为公钥加密;
TLS握手过程:服务端和客户端建立TCP连接之后,会相互确认TLS版本和使用的加密套件;
服务端将公钥发送给客户端,客户端生成一个随机数然后用公钥加密发送给服务端,服务端使用私钥将这个随机数解密,然后再服务端和客户端使用随机数生成会话密钥,此后彼此的连接都使用会话密钥加密;
所以说HTTPS完全是非对称加密是不正确的,TLS协议只是利用了非对称加密的技术来生成临时的会话密钥,而会话的过程使用会话密钥仍然是一个对称加密过程,只是这个会话密钥本身经过非对称加密后十分安全不存在泄漏风险,而且再会话结束后就会被废除不再使用;
SSL证书:假设说现在有个人将网址改了一个字母伪造了一个假网址来冒充官网,HTTPS使用SSL证书来解决这个问题,这样就算购买了域名,如果没有SSL证书那么这个域名在被访问的时候浏览器就会出现风险提示;如果企业需要SSL证书就需要向CA申请;
SSL证书除了表名域名是谁的,日期等等信息之外,重要的是这个证书还包含了特定的公钥和私钥,简单来说,当获取了SSL证书之后,用户就可以通过HTTPS来访问服务器了;
浏览器也会把HTTP默认的80端口改为HTTPS的443端口;
》数字证书 \ 数字签名
为什么有了非对称加密还需要CA证书呢?如果只使用非对称加密技术,那么黑客完全可以在服务端向客户端发送公钥的时候截断连接,然后自己在伪造一个公钥发送给客户端,最后维护两条非对称加密的线路,这样非对称加密也就失去了意义;所以需要CA证书来保证公钥的权威性
在网站想要给用户发公钥时,先去CA将公钥封装在数字证书里面,然后用户收到数字证书后再取出里面封装的公钥,这样就可以确保公钥的权威性,用户也就知道公钥来自服务端;
而如果有黑客想要篡改证书中的公钥怎么办,这里就涉及到数字签名了,本质上这里的原理和JWT的原理类似,就是CA官方使用自己的加密算法生成签名,然后将签名附着在证书上;客户端想要验证公钥-证书-签名时就去请求CA来重新对签名进行验证,这样就保证了公钥不会被黑客更改;
》证书链
CA官方在与服务端客户端颁发证书、签署数字签名的过程中也需要验证自己的权威性,同样的也需要证书来验证自己的签名的权威性,所以直接给用户签名、颁发证书的CA被称为中间CA,他们的签名需要被根CA签名验证,然后根CA的证书的公钥会被预装在用户的操作系统当中,这样就完成了整个信任链的闭环;
Socket
Socket套接字是一种通信机制,它允许不同的进程在网络上进行通信,为应用程序提供了统一的接口,是一种面向连接的网络抽象层;
-
服务端启动,绑定一个端口号和地址,等待客户端连接
-
客户端向服务端发送请求,服务端收到请求后创建Socket对象
-
在连接过程中,客户端和服务端的交互都使用这个单独的Socket对象
-
断开连接后,服务端会将与这个客户端建立的Socket关闭并释放资源
WebSocket
一般来说,我们认为HTTP请求都是客户端请求服务端,然后服务端响应,然而在某些场景下,服务端需要主动的去推送一些消息给到客户端,问题的重点在于,怎样在用户不做任何操作的前提下,客户端能收到消息并变更;
如果通过HTTP来解决,那就是客户端会连续不断的定时发HTTP请求到服务器,服务器收到请求后给客户端响应消息,这种场景最常见的例子就是微信的扫码登录,这就是HTTP定时轮询;
这种方式的缺点是会消耗带宽,并增大下游服务器的负担;
第二种解决的办法是设置长轮询,一般来讲客户端请求如果超过3s服务端不回复会判定为丢包,长轮询机制就是去将这个3s的时间设置很长,服务端在接收到请求后也不会立即响应,而是等待用户操作一旦成功则响应,如果操作不成功,则在30s后响应给客户端让客户端再次请求;
这样就减少了HTTP请求的个数,也解决的负担问题,百度网盘的扫码就是这么做的,所以响应会更及时;
以上两种办法都一定程度上让服务端主动推送给服务端数据,但是如果数据的规模比较大呢?
比如在线游戏的情况,这时候就需要使用WebSocket了,WebSocket和HTTP协议一样的应用层协议
在建立TCP连接后,在HTTP请求头里添加"Upgrade: websocket"来请求升级协议
WebSocket完美继承了TCP的全双工能力,并且解决了粘包的问题,它适用于服务端和客户端需要频繁交互的大部分场景;
RPC
从功能层面来说,HTTP是应用层的协议,是互联网传输通信的基础,主要服务在用户端和服务端的数据传输上;而RPC是远程过程调用协议,它的定位是实现不同计算机应用之间的数据通信,屏蔽了通信的底层复杂度,让开发者能够像调用本地服务一样去完成远程服务的调用,这两个协议目前在功能上是完全不同的;
从实现层面来说,HTTP协议是已经实现的并且成熟的应用层协议,它定义了通信报文的格式,而RPC是通信协议的规范,它并没有具体的将格式完全实现,只有按照RPC通信规范去实现的通信框架才是协议的具体实现比如说Dubbo、gRPC等等;因此我们可以在实现RPC规范,自定义报文通信的实现和自定义序列化方式或者自定义网络通信协议的类型;
从历史发展的角度来说,RPC和HTTP的底层都是TCP协议作为通信基础,RPC的出现一部分也是为了解决TCP的粘包问题,而之所以HTTP会出现是因为大量的公司使用RPC作为通信框架,导致每个公司都需要和用户使用自己的通信框架(研发自己的独立客户端来通信),但是浏览器的出现让大家迫切的需要一套统一的规范来进行用户端和服务端的报文传输,这也是HTTP的基础;
所以一定程度上来说,HTTP也可以说是建立在RPC之上的,HTTP本身也可以实现RPC框架,比如说gRPC、OpenFeign底层都是HTTP协议和RPC协议相结合的模式,所以HTTP和RPC并不是两个完全独立的协议,更像一种嫡系的关系(RPC是HTTP的舅舅?)
常见网络攻击
// TODO
操作系统
概念
如果电脑是一座城市,操作系统就是城市的市政府,它管理着电脑里的一切;
它可以管理CPU、内存、硬盘、鼠标等硬件资源,确保他们能被电脑上的应用程序使用;
它可以给用户提供一个界面,这就像城市里的路标和指示牌,帮助你找到你想去的地方;
它可以管理文件和文件夹,你可以打开文件和文件夹,就像在城市里建造和修路一样;
它可以帮你打开和关闭应用程序,就像城市里的超市和工厂一样;
它可以管理进程,当你打开一个应用程序,操作系统会把这个程序看作一个进程,操作系统会决定进程在CPU上执行的时间和优先级,以确保所有的进程都能得到充分的执行时间;
操作系统还可以通过多任务处理来让多个应用程序同时运行;
操作系统还会对用户提供安全保护,操作系统可以防止病毒和恶意软件对电脑进行攻击,同时还可以控制用户权限,保护电脑的数据和隐私;
进程状态 \ 通信 \ 调度 \ 同步
》进程五态
新建态(New)、就绪态(Ready)、运行态(Running)、阻塞态(Blocked)、终止态(Exit)
》状态切换
时间片轮转:将进程在运行态和阻塞态之间切换
中断处理:外部设备IO发生,触发中断,将进程阻塞
在进程切换时,会保存上下文、加载上下文,还会根据进程的调度算法来决定下一个执行进程
》六种进程间的通信方式
每个进程的用户地址空间都是独立的,一般而言是不能相互访问的,但内核空间是每个进程共享的,所以进程之间如果要通信必须要经过内核空间;
-
管道:通过管道符可以让父子进程共享数据,这种属于匿名管道;通过命名管道可以在不相关的进程间通信数据;缺点,管道通信方式效率低,不适合频繁地交换数据
-
消息队列:消息队列支持频繁的交换数据,但是它不适合大数据的传输,因为消息队列的读取和写入存在内核态中
-
共享内存:共享内存很好的解决了内核态切换的问题,它可以拿出两个虚拟地址空间,映射到相同的物理内存当中,然后让两个进程都认为这一块进程是自己的内存空间;
-
信号量:为了防止共享内存的通信方式在多线程的情况下造成数据错乱,信号量作为同步器就保证了操作的原子性;具体来说就是,资源的信号量默认为0,有进程来操作就-1,操作完就+1
-
信号:在异常情况下的工作模式,就需要使用信号的方式来进行通信,比如kill指令
-
Socket:可以基于TCP、UDP或者进行本地通信,来使用网络的方式来进行进程通信
》进程调度算法
-
FIFO:按照作业或进程到达任务队列的顺序进行调度
-
短作业优先:从队列中选择估计运行时间最短的作业,调入内存运行
-
优先级调度:基于作业的紧迫程度或重要性赋予进程优先级,按优先级进行调度
-
时间片轮转:每次调度选择队首的进程,执行完一个时间片后,将进程移到队尾在调度新的
》进程同步方式
进程同步是操作系统中用于协调多个进程或线程之间执行顺序的一种机制,以确保它们能够按照预定的顺序或规则来访问共享资源或执行相关操作,以下是几种常见的进程同步方式:
-
临界区(Critical Section):通过对多线程的串行化来访问公共资源或一段代码,速度快适合控制数据访问;保证在某一时刻只有一个线程能访问数据的简便方法;缺点是这个方法只能同步同一进程下的线程,不能同步多个进程下的线程;
-
互斥量(Mutex):为协调共同对一个共享资源的单独访问而设计,互斥量只有一个,只有拥有互斥量的线程菜具有访问资源的权限;Mutex锁是可以命名的,它可以跨越进程使用;
-
信号量(Semaphore):为控制一个具有有限数量用户资源而设计,它允许多个线程在同一时刻访问同一资源,但需要限制在同一时刻访问此资源的最大线程数目;使用场景是适合对Socket程序当中线程的同步,他要求必须有公共内存,所以不能用于分布式锁;
-
事件(Event):用来通知线程有一些事件已经发生,从而启动后继任务的开始
孤儿进程 \ 僵尸进程
一般情况下:子进程由父进程创建,子进程再创建新的进程。父子进程是一个异步过程,父进程永远无法预测子进程的结束,所以,当子进程结束后,它的父进程会调用wait()取得子进程的终止状态,回收掉子进程的资源;
孤儿进程:父进程结束了,而它的一个或者子进程还在运行,那么这些子进程就成了孤儿进程;
僵尸进程:子进程退出了,但是父进程没有用wait去获取子进程的状态信息,那么子进程的进程描述符还在系统当中,这种进程称为僵尸进程;
解决方案:最优方案是通过信号机制,而不是使用wait,什么时候得到子进程信号,什么时候进行处理,父进程可以继续执行其他任务,而不是阻塞等待;
用户态 \ 内核态 ⭐
》概念区分
操作系统是应用程序和硬件打交道的桥梁,而应用程序它是通过调用操作系统提供的用户接口程序,去间接的和硬件打交道;像CPU、内存、IO设备,这些都属于硬件;
同时,从程序运行的安全性考虑,将程序的运行状态划分成用户态和内核态;
操作系统是运行在内核态的,而操作系统提供的用户接口程序和应用程序,他们都是运行在用户态的
内核态:可以访问所有的硬件设备,也可以执行硬件上能够运行的各种指令;
用户态:只能执行一部分机器指令,不可以运行IO命令或者影响机器控制的命令;
》什么时候状态切换
系统调用:用户态进程主动要求切换到内核态,通过申请系统调用完成内核态的指令操作
异常:CPU执行程序时触发异常,内核态需要进程来处理异常,比如缺页异常
IO中断:当外围设备完成用户请求的操作后,比如硬盘读写,磁盘插入等
》系统调用全过程
-
执行中断指令,CPU陷入到内核态,获取系统调用号
-
将用户态的寄存器内容(代码段、数据段)保存在内核数据结构
-
在系统调用表中找到相应的系统调用函数进行调用
-
从寄存器中恢复用户态的数据,执行中断返回指令
零拷贝
传统的数据传输过程通常需要经历多次内存拷贝。首先,从磁盘读取数据,然后将数据从内核空间拷贝到用户空间,再从用户空间拷贝到应用程序的内存当中,这些额外的拷贝会消耗大量的CPU资源和内存带宽,降低数据传输的效率;零拷贝的存在就是为了避免这些不必要的数据拷贝,能够将数据直接传输到目标内存区域,以提高数据传输的效率;
虚拟内存 ⭐
》概念
虚拟内存技术说白了就是每个进程所分配的内存并不是真实的物理内存,而是一块虚拟内存,
在我进程需要内存运行的时候在通过页面置换把虚拟内存置换到物理内存当中去工作
》优点
-
内存隔离:虚拟内存技术将进程的虚拟地址空间和实际内存空间映射,实现了内存隔离,即使现在有进程崩溃或者内存访问错误,也不会影响其他的进程,提高了系统的稳定性;
-
提高内存利用率:虚拟内存技术通过分配加载虚拟内存和实际内存空间,提高了内存的利用率;
磁盘调度算法
FCFS 先来先服务:平均寻道时间较长,因为不能考虑到磁头当前位置与请求位置的距离,可能导致磁头频繁大幅度移动;
SSTF 最短寻道时间: 可能导致某些寻道时间较远的请求长时间得不到服务,从而产生饥饿现象,并且可能因频繁改变服务顺序而增加磁头移动的局部性;
SCAN 电梯算法: 磁头沿着一个方向移动来服务请求,减少了不必要的反向移动,缺点是对于两端的请求响应时间较长;
C-SCAN 循环扫描: 到了磁盘的一端后,直接回到磁盘的另一端开启下一轮循环扫描,解决了两端响应长的问题,但是如果请求分布不均匀会导致磁头空移动而降低效率;
LOOK:减少不必要的移动,只有在移动方向上有请求时才移动,提高了效率;
评论记录:
回复评论: