MIT6.S081 xv6book chapter1
第一章从操作系统接口方面认识操作系统,以摘要的形式介绍几个关键点,详情请看xv6book。
我的学习经验是:这一章的主要目的就是从整体上把握操作系统,认识几个系统调用。如果你没看懂这一章的一些细节,这是ok的,因为这些细节会逐渐在后面的章节披露,这一章只需要理解系统调用(操作系统为你提供的服务)。
前言
操作系统的工作是
(1)将计算机的资源在多个程序间共享,并且给程序提供一系列比硬件本身更有用的服务。
(2)管理并抽象底层硬件,举例来说,一个文字处理软件(比如 word)不用去关心自己使用的是何种硬盘。
(3)多路复用硬件,使得多个程序可以(至少看起来是)同时运行的。
(4)最后,给程序间提供一种受控的交互方式,使得程序之间可以共享数据、共同工作。
操作系统通过接口向用户程序提供服务。一方面我们希望接口设计得简单和精准,使其易于正确地实现;另一方面,我们可能忍不住想为应用提供一些更加复杂的功能。答案是接口的组合,通过这些机制的组合提供强大、通用的功能。
然后就是认识shell、进程,内存,文件描述符,管道和文件系统。
shell
The shell is an ordinary program that reads commands from the user and executes them. The fact that the shell is a user program, and not part of the kernel, illustrates the power of the system call interface: there is nothing special about the shell. It also means that the shell is easy to replace; as a result, modern Unix systems have a variety of shells to choose from, each with its own user interface and scripting features.
code design:
The xv6 shell uses the above calls to run programs on behalf of users. The main structure of the shell is simple; see main (user/sh.c:145). The main loop reads a line of input from the user with getcmd. Then it calls fork, which creates a copy of the shell process. The parent calls wait, while the child runs the command. For example, if the user had typed “echo hello” to the shell, runcmd would have been called with “echo hello” as the argument.
runcmd (user/sh.c:58) runs the actual command. For “echo hello”, it would call exec (user/sh.c:78). If exec succeeds then the child will execute instructions from echo instead of runcmd. At some point echo will call exit, which will cause the parent to return from wait in main (user/sh.c:145).
在shell中,经常使用fork+exec的方式执行用户程序。你可能会觉得这很浪费,毕竟fork拷贝了一份进程资源,为什么不把这两个系统调用合并在一起?
fork的好处是能够简单的实现IO重定向。
同时,为了避免拷贝进程然后马上替换它的浪费,fork采用了copy-on-write技术来优化拷贝过程。
进程和内存
An xv6 process consists of user-space memory (instructions, data, and stack) and per-process state private to the kernel. Xv6 time-shares processes: it transparently switches the available CPUs among the set of processes waiting to execute. When a process is not executing, xv6 saves its CPU registers, restoring them when it next runs the process. The kernel associates a process identifier, or PID, with each process.
Some system call:
- fork
- exit
- wait
- exec
I/O 和文件描述符
文件描述符是一个整数,它代表了一个进程可以读写的被内核管理的对象
每个进程都有一张表,而 xv6 内核就以文件描述符作为这张表的索引,所以每个进程都有一个从0开始的文件描述符空间。
按照惯例,进程从文件描述符0读入(标准输入),从文件描述符1输出(标准输出),从文件描述符2输出错误(标准错误输出)。
shell 保证在任何时候都有3个打开的文件描述符,他们是控制台(console)的默认文件描述符。
Some system call:
- read
- write
- close
- open
- dup
user program:
- cat
重要概念:IO重定向,这是shell的一个思想。
File descriptors are a powerful abstraction, because they hide the details of what they are con- nected to: a process writing to file descriptor 1 may be writing to a file, to a device like the console, or to a pipe.
管道
A pipe is a small kernel buffer exposed to processes as a pair of file descriptors, one for reading and one for writing
管道是一个小的内核缓冲区,它以文件描述符对的形式提供给进程,一个用于写操作,一个用于读操作。从管道的一端写的数据可以从管道的另一端读取,管道提供了一种进程间交互的方式。
user program:
- wc
Pipes may seem no more powerful than temporary files: the pipeline
1 | echo hello world | wc |
could be implemented without pipes as
1 | echo hello world >/tmp/xyz; wc </tmp/xyz |
Pipes have at least four advantages over temporary files in this situation.
First, pipes automatically clean themselves up; with the file redirection, a shell would have to be careful to remove /tmp/xyz when done.
Second, pipes can pass arbitrarily long streams of data, while file redirection requires enough free space on disk to store all the data.
Third, pipes allow for parallel execution of pipeline stages, while the file approach requires the first program to finish before the second starts.
Fourth, if you are implementing inter-process communication, pipes’ blocking reads and writes are more efficient than the non-blocking semantics of files.
文件系统
文件是一个简单的字节数组,目录包含指向文件和其他目录的引用。目录是一棵树,它的根节点是一个特殊的目录 root
概念:inode、links
system call:
- mknod
- fstat
- link
- unlink
user program:
- mkdir
- ln
- rm
- cd
总结
UNIX 将“标准”的文件描述符,管道,和便于操作它们的 shell 命令整合在一起,这是编写通用、可重用程序的重大进步,这个想法激发了 UNIX 强大和流行的“软件工具”文化,而且 shell 也是首个所谓的“脚本语言”。
UNIX 的系统调用接口在今天仍然存在于许多操作系统中,诸如 BSD,Linux,以及 Mac OS X。
MIT6.S081 xv6book chapter1
https://xyz.desirer233.fun/2024/01/07/MIT6.S081/book/chapter1/