提示:秋招计算机操作系统
提示:这里可以添加本文要记录的大概内容:
例如:随着人工智能的不断发展,机器学习这门技术也越来越重要,很多人都开启了学习机器学习,本文就介绍了机器学习的基础内容。
提示:以下是本篇文章正文内容,下面案例可供参考
link、link、link
进程是一次程序的运行,内部保存程序运行所需的资源。
——程序是进程产生的基础。
——程序每次运行产生不同的进程。
——进程是程序运行的体现。
——通过多次执行,一个程序可以对应多个进程。通过调用,一个进程可以运行多个程序。
——程序时静态的,进程的动态的;进程是暂时的;程序是永久的。
——动态性:可以动态的创建和销毁;
——独立性:不同的工作进程不会互相影响;
——并发性:可以被独立被调度并占用处理机并发运行;
进程=程序段+数据段+进程控制块(PCB);
操作系统为每个进程维护了进程控制块,通过进程控制块来管理进程。
PCB
标识符:进程的唯一标识符,用来区分其他进程。
状态:进程有不同的状态,例如运行,就绪,阻塞等。
优先级:为了给处理机调度提供支持,优先级用来区分各种进程的先后执行顺序。
程序计数器:程序中即将执行的下一条指令的地址。
内存指针:包括程序代码的进程相关数据的指针,以及与其他进程共享内存块的指针。
上下文:进程是需要切换的,切换进程时需要保留进程的上下文信息,以防进程在切换时丢失现场。 数据信息。
I/O状态信息:包括显示IO请求,分配给进程的IO设备和被进程使用的文件列表等。
程序运行时的内存分区主要分为BSS段、数据段、代码段、堆、栈。
BSS段:一般是指存放程序中未初始化的全局变量的一块内存区域,BSS段属于静态内存分配。
数据段:一般是指用来存放程序中已初始化的全局变量的一块内存区域,数据段属于静态内存分配。
代码段:通常是指用来存放程序执行代码的一块内存区域,这部分区域的大小在程序运行前就已经确定,并且内存区域通常属于只读。
堆:堆是用于存放进程运行中被动态分配的内存段,它的大小并不固定,可动态扩张或缩减。当进程调用mallocl/free等函数分配内存时,新分配的内存就被动态添加到堆上(堆被扩张)释放的内存从堆中被剔除(堆被缩减)。
栈:存放程序的局部变量。除此以外,在函数被调用时,栈用来传送参数和返回值。
——就绪状态(继承已经获取了除了处理机之外的一切资源,一旦获取cpu资源就可以运行,这个就是就绪状态);
——运行状态;
——阻塞状态(等待某种资源:内存资源、数据资源、设备资源等);
操作系统维护了一组状态队列,不同状态的进程PCB会放在不同的队列中,当一个进程的状态发生变化时,它的PCB会从一个状态队列到另一个状态队列;
调度算法分为三类:批处理中的调度、交互系统中的调度、实时系统中的调度;
批处理中的调度:先来先服务、短作业优先、最短剩余时间优先;
交互系统中的调度:时间片轮转、优先级调度;
线程是CPU调度的基本单位,是进程中一条执行的流程。
并发和高效
——进程之间是独立的,所以进程的通信比较麻烦(因为进程通信都是由操作系统实现的,需要进行系统调用);
——维护进程需要更大的系统开销;
——线程的划分尺度小于进程,使得多线程程序的并发性高;
优点
①多个线程可以运行在一个进程中;
②线程可以共享进程的资源和地址空间;
③线程要比进程轻量化的多,所以创建和销毁耗费的资源较少;
缺点
①一旦一个线程崩溃,很有可能会影响同进程的其他线程;
②多个线程共享地址空间,读写数据等会存在竞争关系,所以需要同步机制来避免线程安全问题;
(1)一级内存在cpu内部与cpu同速运行,提高cpu的利用效率(受cpu结构限制,一级缓存的容量都很小);
(2)二级缓存(为了协调cpu与内存的速度,做cpu与内存数据临时交换的地方);
(3)三级缓存(用于存放从外存中拷贝的内容,用于平衡内存与外存的速度);
对容错率要求比较高考虑使用多进程,要想提高cpu利用率、提高运行效率的考虑使用多线程。
(1)进程是程序一次运行的结果计算机系统资源分配的基本单位,线程是cpu调度的基本单位,也是操作系统能够进行调度的最小单位;
(2)多进程和多线程都可以实现并发,提高cpu的利用率;
(3)进程中的线程可以共享该进程的空间地址和资源,但是不同进程一般不会共享地址空间;
(4)线程可以看做是轻量化的进程,所以切换的代价更小;
(5)进程之间是相互独立的,所以进程之间的通信会比线程间通信开销更多;
(6)在保护模式下,一个进程的崩溃一般不会影响其他进程,而同一个进程中的线程崩溃会影响其他线程;
(1)线程锁主要就是对变量、方法、代码块加锁,同一时间内只有一个线程可以获取锁;
(2)因为进程之间是独立的,所以各进程是无法访问其他进程对资源的访问,只能通过操作系统实现;
链接: link
栈和堆是操作系统对进程占用的内存空间的两种管理方式:
(1)管理方式:栈由操作系统自己分配和释放;堆需要人为的申请,使用完毕后需要释放,防止内存泄露;
(2)空间大小:一般来说每个进程拥有的栈的大小要远小于堆的大小;
(3)栈中的内容包括函数返回地址、局部变量和寄存器内容等;堆顶中使用一个字节的空间用来存放堆的大小,堆中的具体内容是由程序员管理的。
(4)栈的地址是向下生长,堆的地址是向上生长。Why(否则的话你要分一个界限去区别堆栈,但是这样的话可以公用这个公共区域,内存利用率更高。)
链接: link
——操作系统会在底层提供对栈的支持,会分配专门的寄存器存放栈的地址,栈的入栈出栈操作也十分简单,并且有专门的指令执行,所以栈的效率比较高也比较快。
——而堆的操作是由C/C++函数库提供的,在分配堆内存的时候需要一定的算法寻找合适大小的内存,并且获取堆的内容需要两次访问,第一次访问指针,第二次根据指针保存的地址访问内存,因此堆比较慢。在堆区上申请与释放内存是一个相对复杂的过程,因为堆本身是需要程序员自己管理的,而栈是编译器来维护的,堆区的维护同样涉及内存的分配与释放,但这里的内存分配与释放显然不会像栈区那样简单。
内核态:具有较高的权限,可以执行一切指令,访问所有的寄存器和存储区。
用户态:具有较低特权的执行状态,仅能执行规定的指令,访问指定的寄存器和存储区,防止应用程序对操作系统的破坏。
我们的程序都是运行在用户态,凡是与系统界别的资源有关的操作都需要系统调用向操作系统提出服务需求,并由操作系统代为完成。
(1)系统调用
(2)异常(例如缺页异常)
(3)外围设备的中断(当外围设备完成用户请求的操作之后会向CPU发出中断信号,CPU会暂停执行下一步将要执行的指令转到中断信号对应的处理程序去执行)
FCFS调度算法(First-Come,First-Served Scheduling)先来先服务
短进程优先算法SCBF(Shortest CPU Burst First)
时间片轮转调度算法RR(Round Robin)
优先级算法PSA(Priority Scheduling Algorithm)
多级反馈队列调度算法MLFQ(Multi-level Feedback Queue)
多级反馈队列调度算法
(1)有N个队列赋予不同的优先级,一般第一个队列的优先级最高,第二个队列次之,然后优先级逐个降低;并为每个队列设置时间片,一般队列的优先级越高,赋予的时间片越短(当然这个可以根据实际情况调整);
(2)待调度的进程进程首先进入优先级最高的队列;
(3)首先调度优先级高的队列,若高优先级队列里没有作业再调度次优先级的进程;
(4)对于每个队列中的进程,按照时间片轮转方法进行调度,如果经过时间片之后还没有有执行完毕,就进入下一级队列;
链接: link
CPU上下文切换就是把上一个任务的CPU上下文保存起来,然后加载新任务的上下文到寄存器与程序计数器,加载完成后跳转到程序计数器所指的新位置,运行新任务;被保存起来的上下文会存储在系统内核中,并在任务执行时再次加载进来。
CPU上下文切换包括进程上下文切换,线程上下文切换,中断上下文切换。
触发进程上下文切换的情况:
(1)进程正常执行完,从队列中取出新进程执行。
(2)进程分配的CPU时间片用完了,但仍未执行完任务。
(3)系统资源不足时,要等到资源满足后才可以运行,此时进程被挂起。
(4)调用sleep函数。
(5)有更高优先级进程运行。
进程上下文内容
代码段、数据段、堆、栈、寄存器信息、地址转换信息、打开文件列表信息、进程控制信息等
线程上下文切换分为两种情况
(1)两个线程属于不同进程,此时进程资源不共享,线程上下文切换等于进程上下文切换。
(2)两个线程属于同个进程,此时进程资源共享,在线程切换时进程资源不变,只切换线程私有数据,此时线程上下文切换消耗资源比进程少。
为什么线程上下文切换消耗资源比进程少?
进程切换的时候可能会涉及到页表的切换,页表切换会导致TLB(快表)中的缓存失效,寄存器中的内容需要重写,内存访问的速度随着就变慢,而线程切换不会涉及到这个过程,所以说进程切换比线程切换代价大。
线程上下文内容
栈、寄存器信息、线程状态信息等
由于硬件(鼠标、键盘)优先级高于进程优先级,收到硬件指令后会打断正在执行的进程,转而执行硬件指令,这种情况被称为中断上下文切换。
主要负责内存的分配与回收,并将逻辑地址转为物理地址。
内存管理主要分为两大类:连续式分配管理和非连续式分配管理;
连续式分配管理是指为一个用户程序分配一个连续的内存空间,常见的如块式管理;
块式管理:内存分为大小不同的块,每个块中包含一个进程;(会产生大量的内部碎片)
非连续分配管理是指一个程序使用的内存分配在不连续的物理内存空间中,常见的如页式管理和段式管理、段页式管理;
段式管理
内存根据程序资源分为大小不同的段;(逻辑地址结构:段号+段内地址)
将程序分为固定大小的页,提高内存利用率,减少了碎片;(逻辑地址结构:页号+页内地址)
将程序资源分为几个段,每个段都有各自的段号,对于每个段,再划分为固定大小的页;(逻辑地址结构:段号+页号+页内地址;)
虚拟内存是一种内存管理方式,它可以使每个进程认为自己有私有的、连续的地址空间,而实际上,它通常被分隔成多个物理内存碎片,还可能有部分暂时存储在外部磁盘存储器上,在需要时需要进行数据交换;而物理内存才是内存条真实的内存空间大小。
在程序装入时,只将程序的一部分加载进内存,另一部分留在外存,在程序执行时,当访问的程序不在内存中,发生缺页中断,操作系统再将相应的内容调入内存(但是其实页的置换也是要耗费cpu的时间的,所以有点类似于时间换空间吧)。
(1)如果直接将物理内存暴露出来,可能会对操作系统造成伤害,导致系统崩溃;
(2)虚拟地址可以使不同的进程在自己独立的地址空间内运行,不受其他进程影响;
(3)虚拟内存可以访问大于物理内存的内存空间,因为党物理内存较少时,会将不常使用的页保存到磁盘空间;
(1)时间局部性:某数据被访问过,在不久时间内该数据可能再次被访问;
(2)空间局部性:一旦内存访问了某内存地址,其附近的存储单元也有可能被访问;
(1)请求分页存储
(2)请求分段存储
(3)请求段页存储
无论是哪种方式都需要一定的硬件支持
——一定容量的内存和外存;
——段表机制
——中断机制(缺页中断)
——地址变换(逻辑地址转为物理地址)
使用虚拟内存,cpu需要将虚拟地址转换为物理地址,这样才能访问真实的物理内存(完成这一操作的是cpu中的内存管理单元MMU)。
逻辑地址包括页号和页内地址,物理地址包括块号(或者称为页帧号)和页内地址。由逻辑地址转换为物理地址,首先找到页表中对应的页号,然后查到对应的物理块号,通过块号与页内地址拼接,就构成物理地址。
共同点:提高内存利用率,减少碎片;
(1)页的大小是固定的,且是由系统决定的。段的长度不固定,决定于程序本身。
(2)分页的地址空间是一维的,分段的地址空间是二维的,在标识一个地址时,既要给出段名也要给出段内地址。
(3)分页可有效提高内存利用率,分段可更好满足用户需求实现信息共享。
(4)分段可能导致外部碎片,分页可能导致内部碎片;
链接: link
段号和页号的来历是不同的,段号是程序员自己定义的,每个段都是有特定含义的,因此不同段的大小不同,代表的意义也不相同,因此要想找到某个数据或指令,需要指定段号和位移两个变量。而页号是系统自动生成的,本身地址是线性连续的,当要访问特定地址时,只需要提供地址即可。系统会自动将地址划分为页号和页内位移,而页号对于程序员来说是没有实际意义的,因此是一维的。
(1)信息共享 :在实现对程序数据的共享时,是以信息的逻辑单位为基础的,在分段方式中,每个段都是逻辑上的一个整体,非常容易做到信息共享,而分页方式,页面大小固定,共享的信息可能存在多个页中,需要花费比分段方式更多的时间实现信息共享。
(2)信息保护:信息保护同样是以信息的逻辑单位为基础的,而且经常以一个过程、函数或文件为基本单位进行保护,对这样的信息进行保护,在分段中我们只需要对整个段设置对应的只读、只写标志即可,但在分页中,一个函数可能要占用多个页面,一个页面还可能有其他的程序和数据,难以实现统一的保护。
分页和分段都需要两次访问内存,为了提高访问内存效率,引入了快表结构;
快表就是存放在TLB(translation lookasidebuffer)变换索引缓冲的部分页表,作为页表的Cache,它的作用与页表相似,但是提高了访问速率。由于采用页表或段表做地址转换,读写内存数据时CPU要访问两次主存;有了快表,有时只要访问一次高速缓冲存储器,一次主存,这样可加速查找并提高指令执行速度。
使用快表之后的地址转换流程
①根据虚拟地址中的页号查找高速缓冲器中的快表;
②如果该页在快表中,直接从快表中读取相应的物理地址;
③如果该页不在快表中,先访问内存中的页表,再获取页表中的物理地址,并对物理地址进行访问,并将记录添加在快表中。
为了解决简单分页产生的页表过大,就有了多级分页,使得页表可以在内存中离散存储,但是这会导致cpu在寻址的过程中需要多层表参与,加大了时间开销。
(1)FIFO(先进先出页面置换)
(2)LRU(最近最久未使用页面置换)
(3)OPT(最佳页面置换)
(4)LFU(最少使用页面置换)
区别在于是否将程序全部加载进内存;
(1)提高计算机系统效率;计算机出来速度远远高于外设工作速度,通过中断可以协调他们的速度,等外设需要与处理机交换信息时,向处理器发起中中断请求,处理机及时响应并处理。
(2)维持系统正常运作;(用户不能直接干涉操作系统,可以通过中断向操作系统发起服务请求)
(3)满足实时处理要求;
(4)提供故障现场处理手段;一旦发生故障或者错误,立即发起中断请求,进行现场保护和记录,为进一步处理提供依据;
中断向量是指中断程序的入口地址,每个程序在运行过程中都有可能被中断,被中断后,被中断的进程都需要对其状态进行保存。
①保护现场,开中断,允许更高级的中断打断低级中断服务;
②处理部分,执行某个中断服务;
③关中断,防止在现场恢复的过程中被新的中断请求中断,等恢复现场之后,再开中断;
两个或两个以上的线程在执行过程中,由于竞争资源或者由于彼此通信而造成的一种阻塞的现象,若无外力作用,它们都将无法推进下去。
互斥条件:一个资源每次只能被一个进程使用。
请求与保持条件:一个进程因请求资源而阻塞时,对已获得的资源保持不放。
不剥夺条件:进程已获得的资源,在末使用完之前,不能强行剥夺。
循环等待条件:若干进程之间形成一种头尾相接的循环等待资源关系。
——多线程竞争资源
——多进程竞争资源
——通信死锁:两个或多个进程在发送消息时出现的死锁。进程 A 给进程 B 发了一条消息,然后进程 A阻塞直到进程 B 返回响应。假设请求消息丢失了,那么进程 A 在一直等着回复,进程 B也会阻塞等待请求消息到来,这时候就产生死锁。通信中一个非常重要的概念来避免:超时(timeout)如果超时时间到了但是消息还没有返回,就会认为消息已经丢失并重新发送,通过这种方式,可以避免通信死锁。
(1)SYN:SYN = 1,代表这个数据包是客户端和服务器之间连接数据包。
(2)ACK:ACK =1,代表这个数据包是一个答复包,用于确认收到的数据包。
(3)FIN:FIN = 1,说明这是一个单方面结束连接的数据包。
(4)RST:RST = 1,说明TCP连接出现异常强制断开连接。
出现RST包的情况
(1)向一个已经关闭的端口发送数据;
(2)向一个已崩溃的连接发送数据;
(3)请求超时;
(4)处于半关闭状态等;
收到RST包后的表现
(1)TCP在任何状态下,只要收到RST包,即可进入closed初始状态;
(2)RST报文段不会导致另一端产生任何响应,另一端根本不需要进行确认,收到RST包即可中断连接;
第一次握手:首先客户端向服务端发送一段连接请求报文,其中:建立连接请求控制(SYN=1)seq=x表示传输的报文段的第一个数据字节的序列号为x,此序列号代表整个报文段的序号;客户端进入SYN-SENT(同步发送状态)
第二次握手:服务器发回确认报文段,同意建立新连接的确认段(SYN=1);确认序号字段有效(ACK=1);服务器告诉客户端报文序号是y(seq=y);ack=x+1表示服务器已经收到客户端序号为x的报文段,准备接收客户端序列号为x+1的报文段;服务器由LISTEN进入SYN-RCVD(同步收到状态)。
第三次握手:客户对服务器的同一连接进行确认,确认序号字段有效(ACK=1);客户此次的报文段的序号是seq=x+1;客户期望接收服务器序列号为ack=y+1的报文段;当客户端发送ack时,客户端进入ESTABLISHED状态;当服务收到客户端发送的ack后,也进入到ESTABLISHED状态;第三次握手可携带数据。
【个人理解】三次握手的目的就是通信双方要确定自己及对方的发送及接收能力正常。
①第一次握手(客户端发送 SYN 报文给服务器,服务器接收该报文):客户端什么都不能确认;服务器确认了对方发送正常,自己接收正常;
②第二次握手(服务器响应 ACK+SYN报文给客户端,客户端接收该报文):客户端确认自己发送、接收正常,对方发送、接收正常;服务器确认对方发送正常,自己接收正常;
③第三次握手(客户端发送 ACK 报文给服务器):客户端确认自己发送、接收正常,对方发送、接收正常;服务器确认自己发送、接收正常,对方发送、接收正常;
(1)客户端停止发送数据,主动关闭TCP连接。
(2)服务器收到客户端的中断请求,客户端到服务器的连接释放,此时TCP处于半关闭状态;
(3)如果服务器也想中断连接就向客户端发出中断请求,等待客户端的的确认;
(4)客户端收到服务器的中断请求之后,过了等待计时器(2MSL)的设置时间,客户端于服务器之间的连接就中断了。
三次握手的过程就是通信双方相互告诉起始序列号并且确认自己和对方的收发能力正常,如果是两次握手,至多只有连接方起始序列号能被确认,另一方(服务器端)的序列号得不到确认。
第三次握手的时候,是可以携带数据的。但是,第一次、第二次握手不可以携带数据。(如果前两次的时候就携带数据,可能出现对服务器的攻击,不管服务器的接收、发送能力是否正常就疯狂进行报文发送,会让服务器话费很多时间来处理这些报文,耗费资源。)
TCP三次握手在第二阶段容易受到攻击,即SYN泛洪攻击,如果客户机伪造出大量SYN报文,服务端就会依次消耗掉很多资源来保存客户端的信息,并进行确认,实际上确认是会失败的,但失败需要一定的时间,因为服务端会连续多次进行第二次握手确认后才认定失败。那么短时间有大量的SYN报文涌向服务端,服务端资源可能被耗尽,就可能导致正常的客户端得不到响应而失败。
服务端一直收不到客户端的ack,就重传syn和ack包,尝试重传超过5次之后会断开tcp连接(注意这是服务器单方面主动断开连接,客户端还是established状态)。
客户端如果没有发送数据,一直处于established状态,当达到保活机制的时间限制时会触发保活机制看这个tcp连接是否存活;
客户端如果发送数据,他会等待服务端的确认报文,如果收不到确认报文也会触发超时重传;
由于 TCP 的半关闭特性,TCP提供了连接的一端在结束它的发送后还能接收来自另一端数据的能力。任何一方都可以在数据传送结束后发出连接释放的通知,待对方确认后进入半关闭状态。当另一方也没有数据再发送的时候,则发出连接释放通知,对方确认后就完全关闭了TCP连接。
(1)确保最后一个确认报文ACK可以到达;
(2)避免新旧连接混淆(等待2MSL可以让本连接中所有的报文全都从网络中消失,使得下一个新的连接不会出现旧的报文);
客户端在发送最后一个ack之后会进入TIME_WAIT状态,MSL是一个片段可以存活的最长时间,所以一来一回刚好2MSL。
客户端time_wait状态过多会导致端口资源被占用,被占满就没有办法创建新的连接。
解决方法
(1)服务器可以设置so_reuseadder套接字来避免TIME_WAIT状态,此套接口会告诉内核,即使此端口正处于TIME_WAIT状态,请继续重用它;
(2)强制关闭,发送RST包越过TIME_WAIT状态,直接进入close状态;
(1)ARQ协议;即自动重传请求(Automatic Repeat-reQuest));接收方收到报文就会确认ACK,发送方发送一段时间后没有收到确认就重传。
(2)数据校验;每次发送数据都会给数据包分配一个序列号并等待对方确认,如果在指定时间内没有收到确认则重传,对方也会根据序列号判断是否有数据丢失或者乱序。
(3)流量控制;流量控制是通过滑动窗口实现的,接收方告诉发送发自己对自己窗口大小,防止发送方发送数据过多来不及处理。
(4)拥塞控制;客户端和服务器之间的网络阻塞导致传输过慢,来不及传输。阻塞控制是通过慢开始、拥塞避免,快恢复、快重传来实现的。
慢开始:指拥塞窗口从小到大,每次接收报文成功,就将窗口大小变为原来的两倍;
拥塞避免:指每经过一个往返时间RTT就把拥塞窗口cwnd+1;
快恢复:指如果发生拥塞,就把门限设置为滑动窗口大小的一半,拥塞窗口变为门限大小的一半;
快重传:TCP协议在发出报文之后会进行计时,在一定时间内没有收到确认信息,就会重新发送报文;而快重传规定发送方一连收到三个确认信息就可以对对方未收到的报文进行重传,不用等待计时器到期,提高吞吐率。
滑动窗口与拥塞窗口
滑动窗口是接收数据端使用窗口的大小,用来告知发送端自身的缓存大小;
拥塞窗口是指某一端数据流在一个RTT内可以最多发送的数据包数;
数据在发送之后可能经过不通过的路径,这样到达目的地的顺序可能会与发送时不同,网络层是不会保证数据的有序性的的,但是TCP可以保证数据的有序性。那么,如何保证有序,tcp通过字节编号,每一个数据字节都会有一个编号,比如发送了三包,每包100字节,假设第一包首个字节标号是1,那么发送的三包的编号就是1,101,201,三包数据,只有接收端收到连续的序号的包,才会将数据包提交到应用层例如收到1,201,101,是不会提交到上层应用层的,只有收到正确连续顺序才会提交,所以就保证了数据的有序性。
主机每次发送数据,都会给数据包分配一个序列号并且在特定时间内等待主机的确认,如果没有收到确认就会重新发送这个数据包。接受主机也会根据这个序列号来判断对方发送的数据是否有丢失或者乱序。
因为TCP开销较大,且有重传机制保证不丢包,适合文件传输及其他保证传输质量的服务;而像视频聊天等,使用UDP更快,即使丢几个包影响也并不大。
例如:对于FPS游戏这种时效性要求非常高的游戏中,玩家最关心的是自己的射击结果和角色的存活与否,当有一个手雷扔过来时,对于被炸死的玩家而言,这颗手雷是必须要接收到的消息,而其他没有被炸到的玩家,仅需要看到手雷的爆炸动画或者声音,其更关心的是自己现在的子弹有没有打到敌人,我们不希望因为手雷的消息重传排队,而把射击玩家的结果确认消息延后了,这对于TCP而言就力所不及了。
TCP还设有一个保活计时器,显然,客户端如果出现故障,服务器不能一直等下去,白白浪费资源。服务器每收到一次客户端的请求后都会重新复位这个计时器,时间通常是设置为2小时,若两小时还没有收到客户端的任何数据,服务器就会发送一个探测报文段,以后每隔75秒钟发送一次。若一连发送10个探测报文仍然没反应,服务器就认为客户端出了故障,接着就关闭连接。
link
Nagle算法规定,一个tcp连接上最多只能有一个未被确认的小分组。在ACK响应到达前,TCP暂时收集待发数据,等到响应ACK到达后使用一个分组将待发数据发送出去。Nagle算法目的就是减少报文数量(避免发送小的数据报文),从而充分利用网络资源,提高了传输效率。
攻击者设置了一个伪造的中间服务器,当我们连接服务器时,这些他会获取服务器内容并进行篡改或者其他操作返回给客户端,包括包括wifi欺骗、HTTP欺骗、DNS欺骗等。
解决方法:不使用公共wifi、使用https网络协议、不要忽略警告、更新防毒软件等;
SYN泛洪攻击
在短时间内伪造大量不存的IP地址并行服务器发起请求,会造成大量的半连接占用半连接队,真正的请求无法及时处理;
解决方法:
(1)减少SYN timeout过时的时间;
(2)记录ip,如果连续收到某ip重复报文,将该ip发送的连接请求一律丢弃;
(1)UDP面向数据报文,应用层交给UDP多长的报文,UDP会原样发送,不会拆分也不会合并。
(2)UDP没有真正意义的发送缓冲区,UDP有接收缓冲区,但是这个缓冲区不能保证UDP报的顺序和发送UDP包的顺序一致,如果缓冲区满了,再到达UDP数据就会被丢弃。
(3)UDP中限制了传送的数据报长度,只有64k,如果超过64k需要手动进行分包。
链接: link
可以使用超时重传、报文添加序列号,确认应答、滑动窗口流量控制等
RUDP(它的实现完全依赖于重传机制)
RTP(有序传送)
UDT(加入拥塞控制和可靠性控制)
尽管IP地址可以唯一地标记网络上的计算机,但是IP地址是一串数字不便记忆,所以又发明了域名地址(如:www.wikipedia.org是一个域名,和IP地址208.80.152.2相对应)。
MAC(media access control address)地址,也称为局域网地址、以太地址、物理地址,它用来确认网络设备位置;MAC地址用于网络中唯一标示一个网卡,以太设备可以有一个或多个网卡,每个网卡都会有唯一的MAC地址。IP地址和MAC地址都是用二进制表示的,IP地址是32位的,而MAC地址是48位的。IP地址与MAC地址的映射要通过ARP地址解析协议来完成。
1)GET:传递参数长度受限制,因为传递的参数是直接表示在地址栏中,而特定浏览器和服务器对url的长度是有限制的。因此,GET不适合用来传递私密数据,也不适合拿来传递大量数据。一般的HTTP请求大多都是GET。
2)POST:POST把传递的数据封装在HTTP请求数据中,以名称/值的形式出现,可以传输大量数据,对数据量没有限制,也不会显示在URL中。表单的提交用的是POST。
3)HEAD:HEAD跟GET相似,不过服务端接收到HEAD请求时只返回响应头,不发送响应内容。所以,如果只需要查看某个页面的状态时,用HEAD更高效,因为省去了传输页面内容的时间。
4)DELETE:删除某一个资源。
5)OPTIONS:用于获取当前URL所支持的方法。若请求成功,会在HTTP头中包含一个名为“Allow”的头,值是所支持的方法,如“GET, POST”。
6)PUT:把一个资源存放在指定的位置上。本质上来讲,PUT和POST极为相似,都是向服务器发送数据,但它们之间有一个重要区别,PUT通常指定了资源的存放位置,而POST则没有,POST的数据存放位置由服务器自己决定。
7)TRACE:回显服务器收到的请求,主要用于测试或诊断。
8)CONNECT:CONNECT方法是HTTP/1.1协议预留的,能够将连接改为管道方式的代理服务器。通常用于SSL加密服务器的链接与非加密的HTTP代理服务器的通信。
1)“GET使用URL传参,而POST将数据放在request_BODY中”,这个是因为HTTP协议用法的约定,并非它们的本身区别。
2)“GET方式提交的数据有长度限制,则POST的数据则可以非常大”,但是HTTP协议并没有规定GET/POST请求的长度,这个长度是由浏览器设置的,一般大小为2048个字符。
3)GET一般用来http请求,post用于向服务器提交数据。
4) get获取的结果可以被缓存,但是post不能缓存。
5)GET和POST最大的区别主要是GET请求是幂等性的,POST请求不是。
幂等性是指一次和多次请求某一个资源应该具有同样的副作用。简单来说意味着对同一URL的多个请求应该返回同样的结果。
200:服务器已成功处理了请求。通常,这表示服务器提供了请求的网页。
301:(重定向)请求的网页已永久移动到新位置。服务器返回此响应(对GET或HEAD请求的响应)时,会自动将请求者转到新位置。
302:(临时重定向)服务器目前从不同位置的网页响应请求,但请求者应继续使用原有位置来进行以后的请求。
400:客户端请求有语法错误。不能被服务器所理解。
404 :服务器找不到请求的网页。
500:服务嚣遇到错误,无法完成请求。
无状态协议
无状态协议不需要为多个请求保留会话信息或每个通信伙伴的伙伴;
1)简化了服务器的设计;
2)需要的资源较少,系统不需要多链路通信和会话细节;
3)每个通信都是独立的,与之前或之后的通信无关;
例子:HTTP、UDP、DNS等
有状态协议
服务器端一般都要保存请求的相关信息,每个请求可以默认地使用以前的请求信息。
1)通过跟踪连接信息为客户端提供更好的性能;
2)有状态的请求总是依赖服务器端的状态;
3)通信双方都在其生命周期维护有关会话本身的信息;
例子:FTP、Telnet等
cookie,session和token详解
Cookie,Session,Token详解
cookie是浏览器存储在本地的文件,主要用于存储服务器对用户进行的标记,大小有限一般只为4kb,用户在第一次进行服务器请求时,服务器会生成对应的id,然后发送给客户端,客户端就会存储在本地文件中,其交互流程如下:
1)Client 发送 HTTP 请求给 Server ;
2)Server 响应,并附带 Set-Cookie 的头部信息 ;
3)Client保存 Cookie,之后请求 Server 会附带 Cookie 的头部信息 ;
4)Server 从 Cookie 知道 Client是谁了,返回相应的响应
Session 机制将用户所有的活动信息,上下文信息,登录信息等存储在服务端,生成一个唯一标识ID发送给客户端,后续交互没有重复的交互信息,取而代之的是唯一标识ID;其交互流程如下:
1)客户端第一次请求session对象,服务器会为客户端创建一个session,算出一个id标识session对象;
2)浏览器下次请求别的资源,浏览器会将sessionID放置请求头,服务器接受请求会解析sessionID,服务器接收sessionID确定请求方的身份信息和上下文信息。
Session 在两种情况下会自动销毁:
1、客户端关闭浏览器程序,造成了JSESSIONID凭证丢失;
2、session超时(会话超时);
Token避免了session机制带来的海量信息存储问题,也避免了cookie机制的安全问题,是一种具有时效性的验证身份和手段;其交互流程如下:
1)客户端将账号和密码发送给服务端。
2)服务器对其校验,生成一个token值发给客户端,作为后续的请求交互身份令牌。
3)客户端拿到服务端返回的token的值后,将其保存在本地,每次请求服务端携带该token值。
4)服务端收到请求,解析相关信息,根据加密算法,密钥,用户生成的参数sign与客户端的sign进行对比,一致则通过,否则拒绝。
5)验证通过后,服务端可以根据token中的uid获取对应的用户信息,进行请求业务的响应。
1)cookie保存在客户端,session保存在服务器;
2)cookie可以设置为长时间保持(例如浏览器记住我们的登录密码),session一般保持时间较短,客户端关闭或者session超时都会失效;
3)cookie保存在客户端更容易遭到剽窃(比如密码被盗),session存储在服务器端安全性相对更高;
1)session是存储在服务器端,但是cookie和token存储在客户端。
2)客户端发送session和token都要借助cookie。
3)token可以减轻session存储量。
http1.1 VS http1.0
(1)建立了长连接
(2)断点续传
(3)支持host域(对于多个虚拟机可能共享一个IP地址)
http1.0/1.1不足:
(1)单路连接(每个tcp连接同一时间只能对应一个HTTP请求,而且HTTP中对请求时严格的先进先出FIFO所以,如果中间某个请求时间过长会阻塞后面的请求);
(2)只允许客户端主动发起强求;
(3)http头部冗余(HTTP头部的冗余信息,比如User_Agent、host等的反复发送,浪费宽带和资源);
(4)明文传输;
http2.0 VS http1.1
(1)多路复用(一个连接可以处理多个请求)
(2)数据压缩(传输速度会更快)
(3)服务器推送(服务端根据客户端的请求,提前返回多个响应,推送额外的资源给客户端,如下图,客户端请求stream 1(/page.html)。服务端在返回stream 1的消息的同时推送了stream2(/script.js)和stream 4(/style.css))
link
短连接:客户端和服务器每进行一次HTTP操作,就会建立一次TCP连接,任务结束就中断;
长连接:在客户端和服务器端传输任务结束后,TCP连接不会关闭,当客户端再次访问服务器时会直接使用这个已经建立的连接(如果一个给定的连接在指定时间内没有任何操作,服务器就向客户发送心跳包,探测客户端的状态决定是否要终止这个连接。)
链接: link、 link
http1.1中实现了在一个tcp通道中实现多个http的并发,但是它是阻塞的,只能按照FIFO的顺序进行返回;
在HTTP2.0中一个TCP通道中也可以同时响应多个http请求和响应,而且响应顺序和请求顺序无关。
原理
在http2.0中添加了一个分帧层,它会将所有传输的信息分割成更小的消息封装在帧中,(将一个request分割为frame,每个frame都有相应的streamid)并使用二进制编码。
(1)Websocket实现的是双向通信,HTTP一般是客户端向服务端发起请求连接;
(2)Websocket在建立连接的时候需要使用HTTP;
Websocket的具体过程为,客户端发起http请求,3次握手实现tcp连接;服务端收到请求后,同样采用http协议回馈数据;客户端收到消息,连接成功,开始借助tcp协议进行全双工通信;(建立连接之后的全双工通信就不需要http协议,只需要从tcp通道传输.)
TCP/IP是传输协议,Http是应用层协议,Socket是对TCP/IP协议的封装,Socket本身并不是协议,而是一个调用接口(API),通过Socket我们才能使用TCP/IP协议。
(1)HTTP对传输数据不进行加密,HTTPS对传输数据使用SSL协议进行加密;
(2)HTTP使用的是TCP的80端口,HTTPS使用的是TCP的443端口
(3)HTTP属于应用层的协议,HTTPS是在HTTP的基础上加了SSL安全协议,而SSL是运输层的协议,所以说HTTPS是应用层和传输层的结合。
(1)用户输入url地址;
(2)DNS解析域名得到相应的ip地址;
(3)TCP三次握手建立连接(源ip源端口,目标ip目标端口);
(4)建立连接后,客户端发起http/ssl连接请求获取服务端数据;
(5)服务端相应数据给客户端,客户端获取静态资源;
(6)Tcp四次挥手关闭客户端和服务器的连接;
(7)浏览器解析数据资源并渲染页面;
(1)服务器端创建socket,调用bind(ip,port)函数绑定自己的值和端口号,然后调用listen()函数监听在(ip,port)上,等待客户端的连接请求;
(2)客户端创建socket,调用bind(ip,port)函数保定自己的地址和端口号,然后调用connect(dst IP,dst
Port)驱动协议栈进行tcp连接请求;
(3)服务器端调用accept()函数驱动协议栈对tcp连接响应,实现三次握手;
(4)服务器端和客户端连接成功之后,通过send和receive试下数据发送与接收;
(5)数据传输完成之后,客户端调用close函数关闭连接,释放端口号等资源;
SSL(Secure Socket Layer)安全套接层是一种为网络通信提供安全和可靠性的安全协议;
关于SSL、[关于SSL](https://blog.csdn.net/oscar999/article/details/9364101
SSL解决的问题
信息被窃听(wiretap),第三方随时随地获得通讯内容;(信息加密)
数据被篡改(tampering),第三方可修改传输中的数据;(数据签名)
身份被冒充(pretending),第三方可冒充通讯者身份传输数据;(CA数字证书认证)
优点:使用对称、非对称加密、数字证书、数字签名等提高安全性;
缺点:大量加密、解密处理,耗费cpu资源及内存资源,导致处理速度变慢;
①数字证书信息包括:公钥、服务器信息、发布单位信息、公钥信息等;
②数字签名信息:先用hash生成发送报文的摘要,然后用私钥加密就生成了数字签名。
拿到报文之后,使用hash得到一份摘要,用公钥对数字签名进行解密,得到一份摘要,判断这两份摘要是否相同。
非对称加密算法:RSA,DSA/DSS
对称加密算法:AES,RC4,3DES,DES
HASH算法:MD5,SHA1,SHA256
对称加密:
(1)效率比较高
(2)安全性相对较差(只有一把钥匙,一旦密钥也被劫持,那么,信息很容易被破译)
非对称加密:
(1)安全性高
(2)加密算法相对比较复杂,加密解密效率相对较低(私钥只能由一方保管,另一方可以请求获得公钥)
1、客户端向服务端发起请求,并告诉服务端自己支持的加密方式,SSL协议版本和一个随机数h1;
2、服务端在收到客户端的连接请求之后,会向客户端发送自己支持的加密方式的公钥、数字证书、数字签名和一个随机数h2;
3、客户端再收到服务端发送的消息后,先用数字证书读客户端的身份进行验证,验证通过之后会生成一个随机数h3,并将随机数用公钥加密后发送个服务端;
4、服务端在收到消息后首先利用私钥对加密的随机数进行解密,并利用前面生成的随机数生成后面https数据传输所需的密钥key。——之后便可以进行数据的传输;
(1)DNS在区域传输的时候使用的是TCP协议;
——辅域名服务器会定时向主域名服务器进行查询以便了解数据是否有变动,如果有变动,会执行区域传输,进行数据同步。区域传送使用的是TCP而不是UDP,因为数据同步传送的数据量比数据较大。
——TCP是一种可靠连接,保证数据的准确性。
(2)域名查询的时候用的是UDP协议;
——进行域名查询时返回的内容一般都不超过512个字节,用UDP输出即可,使用TCP还要进行三次握手,资源耗费比较多,响应较慢。
(1)首先在服务器缓存中查找相应的记录,找对应的ip地址;
(2)操作系统的缓存中进行查找;
(3)本地域名服务器缓存中查找(一般到这里80%都可以查找成功);
(4)从根服务器—>顶级域名服务器—>权限域名服务器继续进行递归查询,直到在目标域名所在的服务器找到相应ip地址,解析结束。
(1)一个ip有多个域名,访问时带上host字段,服务器就知道访问哪个网站。
(2)一个域名有多个ip,DNS负载均衡,为了减少服务器的负担,将客户端的访问引导到不同的服务器上,分摊流量。
负载均衡作用:使用一个集群,提高服务器的处理能力,提高网络灵活性。
(1)原子性(事务包含的所有操作要么全部成功,要么全部失败回滚);
(2)一致性(事务必须使数据库从一个一致性状态变为另一个一致性状态);
(3)隔离性(多个用户访问数据库时,每个用户开启的事务不能被其他事务操作所干扰);
(4)持久性(事务一旦提交对数据库中数据的改变是永久性的);
(1)所有的域都应该是原子性的,即数据库表的每一列都是不可分割的原子数据项。
(2)第二范式就是在第一范式的基础上属性完全依赖于主键;
(3)任何非主属性不依赖于其它非主属性;
范式的目的:消除存储异常,使数据冗余尽量小,便于插入、删除和更新。
提示:这里对文章进行总结:
例如:以上就是今天要讲的内容,本文仅仅简单介绍了pandas的使用,而pandas提供了大量能使我们快速便捷地处理数据的函数和方法。