Lec 3 OS Organization and System Calls总结

学习资料:

https://pdos.csail.mit.edu/6.828/2020/schedule.html
https://mit-public-courses-cn-translatio.gitbook.io/mit6-s081/
https://th0ar.gitbooks.io/xv6-chinese/content/
https://www.bilibili.com/video/BV19k4y1C7kA

参考资料

https://blog.csdn.net/qq_53111905/article/details/120713042

  • 操作系统隔离性(isolation)

    • 使用操作系统的一个原因,甚至可以说是主要原因就是为了实现 multiplexing (CPU在多进程分时复用) 和 内存隔离 。如果你不使用操作系统,并且应用程序直接与硬件交互,就很难实现这两点。所以,将操作系统设计成一个库,并不是一种常见的设计。你或许可以在一些实时操作系统中看到这样的设计,因为在这些实时操作系统中,应用程序之间彼此相互信任。但是在大部分的其他操作系统中,都会强制实现硬件资源的隔离。
    • 所以,操作系统不是直接将CPU提供给应用程序,而是向应用程序提供“进程”,进程抽象了CPU,这样操作系统才能在多个应用程序之间复用一个或者多个CPU。
  • 操作系统防御性(Defensive)

    • 如果操作系统需要具备防御性,那么在应用程序和操作系统之间需要有一堵厚墙,并且操作系统可以在这堵墙上执行任何它想执行的策略。
    • 通常来说,需要通过硬件来实现这的强隔离性。这里的硬件支持包括了两部分,第一部分是user/kernel mode,;第二部分是page table或者虚拟内存(Virtual Memory)。
  • 硬件对于强隔离的支持

    • user/kernel mode
      • 当运行在kernel mode时,CPU可以运行特定权限的指令(privileged instructions);当运行在user mode时,CPU只能运行普通权限的指令(unprivileged instructions)。
      • 在用户空间(user space)尝试执行一条特殊权限指令
        • 用户程序会通过系统调用来切换到kernel mode。当用户程序执行系统调用,会通过ECALL触发一个软中断(software interrupt),软中断会查询操作系统预先设定的中断向量表,并执行中断向量表中包含的中断处理程序。中断处理程序在内核中,这样就完成了user mode到kernel mode的切换,并执行用户程序想要执行的特殊权限指令。
    • 虚拟内存
      • 处理器包含了page table,而page table将虚拟内存地址与物理内存地址做了对应
      • 每一个进程都会有自己独立的page table,这样的话,每一个进程只能访问出现在自己page table中的物理内存。操作系统会设置page table,使得每一个进程都有不重合的物理内存,这样一个进程就不能访问其他进程的物理内存,因为其他进程的物理内存都不在它的page table中。一个进程甚至都不能随意编造一个内存地址,然后通过这个内存地址来访问其他进程的物理内存。这样就给了我们内存的强隔离性。
  • User/Kernel mode切换

    • ECALL接收一个数字参数,当一个用户程序想要将程序执行的控制权转移到内核,它只需要执行ECALL指令,并传入一个数字。这里的数字参数代表了应用程序想要调用的System Call,ECALL会跳转到内核中一个特定的、由内核控制的位置。
      • 操作系统在什么时候检查是否允许执行fork或者write
        • 在Unix中,任何应用程序都能调用fork,我们以write为例吧,write的实现需要检查传递给write的地址(需要写入数据的指针)属于用户应用程序,这样内核才不会被欺骗向别的不属于应用程序的位置写入数据。
  • 宏内核 vs 微内核

    • 让整个操作系统代码都运行在kernel mode。大多数的Unix操作系统实现都运行在kernel mode。比如,XV6中,所有的操作系统服务都在kernel mode中,这种形式被称为Monolithic Kernel Design(宏内核)。
      • 出现Bug的可能性更大了。
      • 这些子模块现在都位于同一个程序中,它们可以紧密的集成在一起,这样的集成提供很好的性能。
    • 微内核的目的在于将大部分的操作系统运行在内核之外。所以,我们还是会有user mode以及user/kernel mode的边界。但是我们现在会将原来在内核中的其他部分,作为普通的用户程序来运行。
      • 更少的代码意味着更少的Bug。
      • 性能更差
        • 在user/kernel mode反复跳转带来的性能损耗。
        • 在一个类似宏内核的紧耦合系统,各个组成部分,例如文件系统和虚拟内存系统,可以很容易的共享page cache。而在微内核中,每个部分之间都很好的隔离开了,这种共享更难实现。进而导致更难在微内核中得到更高的性能。

内核是如何编译

在这里插入图片描述

首先,Makefile(XV6目录下的文件)会读取一个C文件,例如proc.c;之后调用gcc编译器,生成一个文件叫做proc.s,这是RISC-V 汇编语言文件;之后再走到汇编解释器,生成proc.o,这是汇编语言的二进制格式。

Makefile会为所有内核文件做相同的操作,比如说pipe.c,会按照同样的套路,先经过gcc编译成pipe.s,再通过汇编解释器生成pipe.o。

之后,系统加载器(Loader)会收集所有的.o文件,将它们链接在一起,并生成内核文件。

这里生成的内核文件就是我们将会在QEMU中运行的文件。同时,为了你们的方便,Makefile还会创建kernel.asm,这里包含了内核的完整汇编语言,你们可以通过查看它来定位究竟是哪个指令导致了Bug。

接下来,让我们不带gdb运行XV6(make会读取Makefile文件中的指令)。这里会编译文件,然后调用QEMU(qemu-system-riscv64指令)。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值