完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
操作系统
内存管理 简述进程线程切换的流程 如果想要从A进程切换到B进程,必定要先从用户态切换到内核态,因为这个切换工作是由操作系统完成的,操作系统需要先挂起正在占用CPU的A进程,才能切换到B进程。 由于从用户态切换到内核态的时候,CPU是在用户进程手中,所以这个是通过硬中断来实现的。再从用户态切换到内核态之前需要首先保存用户进程的上下文,以便下一次执行是可以继续之前的工作。 这个上下文就是进程的执行环境,包括所有的寄存器变量,进程打开的文件、内存信息等。一个进程的上下文可以分为用户级上下文、寄存器上下文、系统级上下文。用户级上下文存储的是用户进程的内存数据和堆栈数据等;寄存器上下文是一些通用寄存器;系统级上下文是内核栈、PCB(进程控制块)等; 进程在地址空间会划分为哪些区域 我来简单讲一下把文件加载到内存中的一个过程,以Windows为例,PE文件中有一个叫节的概念,节是PE文件中存放代码和数据的基本单元,用以存储不同类型的数据,比如data节、code节等,一个节的所有原始数据必须加载到连续的内存地址空间,这也就造成了在虚拟地址空间中的区块划分。 在虚拟地址空间中会按节划分为代码段、数据段、未初始化的数据段以及堆栈这些区块。 堆和栈有什么区别 我们常说堆栈堆栈,其实堆和栈是两个不同的概念,最直观的理解,堆是由用户控制的,Java中可以用new关键字在堆中申请内存来实现内存分配,c语言是用malloc,而栈是由操作系统控制的,在栈中存储的是这个进程的局部变量等,比如我们用new关键字来申请一块内存,内存本身是在堆中开辟的,而指向内存的指针是存储在栈中的。 操作系统为什么分内核态和用户态,这两者如何切换 因为在CPU的指令中,有一些是非常危险的,比如清理内存、设置时钟等,如果所有的程序都能使用,就有可能造成程序崩溃,所以CPU将指令分为特权指令和非特权指令,对于那些危险的指令,只允许操作系统使用。CPU的特权指令有四级,从Ring0到Ring3,正常使用时一般只有两级,即用户态Ring3和内核态的Ring0,Ring3状态不能访问Ring0的地址空间,包括代码和数据。 用户态切换到内核态的三种方式 系统调用(软中断) 硬中断 异常 虚拟地址怎么映射到物理地址 虚拟地址的构成为页目录索引、页表索引和表内偏移 以win32系统为例,页目录和页表都为1024个,页表大小为212=4KB,一共是4GB(210210*4*210=4230=4GB,1GB=210MB=210KB=210B)的虚拟内存空间,而从虚拟地址空间到物理地址空间实际上就是通过页目录索引和页表索引找到内存页。 在页表项中有个标志位,用来标识包含此数据的页是否在物理内存中,如果在的话,就直接做地址映射,否则,抛出缺页中断,操作系统会把此数据页调入内存。 socket编程中怎么处理并发请求 对多线程的处理和单线程处理的不同之处在于各个不同的进程可能会访问相同的资源,如果是对相同资源进行修改的话,需要用到锁。 简述IO多路复用 Linux的IO访问通常是操作系统先将数据拷贝到操作系统的内核缓冲区,然后再从内核缓冲区拷贝到应用程序的地址空间,再这两个阶段中,有不同的IO方式,主要为阻塞IO,非阻塞IO,异步IO和IO多路复用。 阻塞IO即当数据还没准备好,也就是说数据还在操作系统的内存缓冲区时,用户进程就会一直阻塞,等待数据从内核缓冲区拷贝到应用进程的地址空间。 非阻塞IO就是如果数据还没准备好,操作系统就会给应用进程一个error,并不会阻塞应用程序,而一般应用程序会持续询问数据是否准备好,所以从另一个角度来说也是阻塞的。 异步IO才是真正的不阻塞,当用户进程发起read后,操作系统会立即进行回复,这样用户就可以做其他事情,当数据拷贝到应用程序的地址空间后,操作系统就会给用户进程一个信号,而用户进程就可以用回调函数对信号进行响应。 IO多路复用则是允许一个程序同时等待多个文件描述符,当一个文件描述符(文件描述符(file descriptor)是内核为了高效管理已被打开的文件所创建的索引,用于指代被打开的文件,对文件所有 I/O 操作相关的系统调用都需要通过文件描述符。)就绪,select函数就会返回,当然IO多路复用在本质上还属于阻塞IO,只不过可以同时进行多个IO操作。 Linux的IO复用机制中有select、poll、epoll三种, select和poll的时间复杂度都是O(n),因为它们都是在对IO列表进行轮询,不同点在于select能监视的文件描述符有上限,一般为1024,当然这个时在Linux内核中进行的宏定义,是可以修改的,而poll时基于链表来存储的,所以没有这个上限。 而epoll是基于事件驱动的,所以不需要轮询,epoll会把事件和每一个IO流对应起来。而且epoll是通过一块共享内存来实现内核空间和用户空间的通信的,比起select和poll的大量数据拷贝来说效率更高。 不过select的优点在于兼容不同的操作系统,而poll、epoll只能用于Linux操作系统。 进程线程管理 简述进程间通信的各种方法 进程间通信的方式通常为管道、系统IPC、套接字三种,管道分为无名管道和命名管道**;系统IPC有消息队列**、信号、共享内存三种。 无名管道的本质是内核缓冲区的环形队列,每次读取数据后缓冲区都会移动,并且无名管道只能在有亲缘关系的进程间使用。 命名管道则以文件的形式存在,由于有一个路径名,没有亲缘关系的进程间也可以使用命名管道。 消息队列是存放在内核中消息链表,具有特定的格式,支持多种数据类型,且允许多个进程进行读写。 信号是软件层次对中断机制的一种模拟,是一种异步通信方式,并且信号可以在用户空间进程和内核之间直接交互。 共享内存就是两个进程对同一块内存进行读写,是最快的IPC形式,但不适合大量数据传输。 Socket是TCP/IP协议族的封装,不仅可以用于本机上进程的通信,更多的被用于网络通信中。 进程的互斥与同步 在操作系统中,进程是占有资源的最小单位,对于那种只能同时被一个进程持有的资源我们被称为临界资源,对于临界资源的访问,必须是互斥的。(临界资源的访问过程分为: 进入区、临界区、退出区、剩余区) 而进程之间访问临界资源时可以构成同步与互斥两种关系,同步即两个进程的资源访问必须时先后关系,比如经典的生产者消费者问题,读者写者问题。而互斥则是两种在进行资源抢占,比如购票问题。 通常在软件层面可以使用替换算法来实现,即每个进程持有一个标志,每次当使用资源时则将自己的标志位与资源的标志互换,如果在互换的过程中发现自己获得的标志是正在使用的状态,则在此循环等待。这种方法的缺点在于每个进程都需要进行循环等待,比较低效。所以一般是通过硬件层面的信号量即PV操作来实现进程间的临界资源管理。 死锁的解决方法 死锁的产生是在这样的一个环境中:比如我们有两个进程AB,他们都需要资源1和资源2,当进程A持有资源1,进程B持有资源2的时候,他们都需要对方手上的资源,而一般操作系统又不允许抢占,这个时候就发生了死锁。 从这个例子其实可以总结出死锁的4个必要条件: 1.一个资源只能被一个进程占有,不能共享 2. 一个进程请求资源失败时,它会等待而不是释放 3. 一个进程在释放资源前,其他进程不能抢夺资源 4. 循环等待 从死锁产生的原因可以设计一些方法去避免死锁的发生 5. 静态分配资源,一开始就把一个进程所需的全部资源都分配给他,但这样会降低资源的使用效率 6. 允许抢占,需要设置进程的不同优先级,高优先级的进程可以抢占低优先级的进程的资源。 7. 把资源进行编号,申请资源必须按照资源的编号顺序来申请。 如果死锁已经发生了,就需要去解开死锁,其本质思想就是分配资源打破循环等待 可以运行抢占,从一个或多个进程中抢出资源来给其他进程。 也可以终止一些进程,来达到释放资源的目的。 进程调度算法 先来先服务调度算法 对长作业有利,但对短作业不利 时间片轮转调度算法 每个进程都只能运行一个时间片 时间片的大小对系统性能的影响很大,时间片过大就和先来先服务算法一样,过短会导致进程切换开销过大 短作业优先调度算法 对长作业不利,不能保证紧迫性作业(进程)被及时处理 最短剩余时间优先算法 允许抢占,总是选择预期剩余时间最短的进程 高响应比优先调度算法 R=(w+s)/s,(R为响应比,w为等待处理时间,s为预计服务时间),选择R最大的进程执行 优先级调度算法 进程优先级分为静态优先级和动态优先级 多级反馈队列调度算法 分为多个队列,每个队列中按照时间片轮转算法进行进程调度,每个队列的时间片不一样(由低到高),如果进程在第一个队列的时间片内还没有完成,就会从第一队列删除进入第二队列,以此类推,只有当第一个队列为空时才会执行第二队列的进程 短作业有限且长作业不会太长时间不被处理 磁盘调度算法 先来先服务算法(FCFS) 根据进程访问磁盘的先后次序进行调度 优点是公平、简单 缺点是吞吐量低、寻道时间长 最短寻道时间优先算法 访问与当前磁头所在磁道最近的磁道 优点是可以得到比较好的吞吐量 缺点是对内外边缘磁道的请求可能会被无限延迟 扫描算法(SCAN)(电梯调度算法) 优先考虑磁头当前的移动方向,再考虑欲访问的磁道与当前磁道的距离,–》,《–,从小到大再从大到小 优点是避免了饥饿现象的出现 缺点是两侧磁道访问的频率仍低于中间磁道 循环扫描算法(CSCAN) 在SCAN算法的基础上,磁头只单向移动,当磁头移动到最外的被访问的磁道时,磁头立即返回到最里面欲访问的磁道。–》, --》,每次从小到大 优点是访问请求均匀分布 页面调度算法 先进先出调度算法(FIFO,First in First out) 最近最少使用算法(LRU,Least Recently Used)当访问某个元素时就把它从原来的位置删除移到最右边,当缓存不命中且未满时插入到最右边,缓存不命中且已满删除最左边的元素 最不经常使用页置换算法(LFU,Least Frequently Used)淘汰一定时间内访问次数最少的页面。 时钟置换算法——为每一页设置访问位和修改位,将内存中所有页面通过连接指针接成循环队列,当页面被访问时访问位置置为1,被修改时修改位置置为1,每次淘汰时,从指针当前位置开始循环遍历, 第一次寻找访问位和修改位都为0的页面淘汰, 如果没有则寻找第一个访问位为0的页面将其淘汰, 如果都不存在则将扫描过的页面访问位为1的改为0,重复第1和第2步。 最佳置换算法-理想算法,找一个未来最长时间才会访问的页面进行淘汰。 |
|
|
|
只有小组成员才能发言,加入小组>>
9533 浏览 0 评论
8902 浏览 0 评论
13305 浏览 0 评论
4345 浏览 0 评论
4567 浏览 0 评论
1671浏览 1评论
299浏览 1评论
436浏览 1评论
IPC-6012E CN 2020中文 CN 刚性印制板的鉴定及性能规范
510浏览 1评论
331浏览 0评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2024-11-24 12:19 , Processed in 1.398055 second(s), Total 77, Slave 60 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号