内容简介
为什么要阅读内核源代码
● 对计算机系统的全貌有更深入的了解
● 对学到的算法和思路举一反三
● 加深对操作系统的理解
● 提升自身的技术水平
为什么选择UNIX V6?
● 代码行数约为1 万行
● 有充实的资料可参考
● 网罗了操作系统的基本功能
● 简化的设计
● 便于读者对系统有完整的了解
● 有模拟器可供参考
本书是一本Unix内核源代码的阅读指南。作者结合UNIX V6已公开的相关文档,对其内核源码进行详细剖析,旨在让读者更深入地理解进程、中断、块I/O系统、文件系统、字符I/O系统、启动系统等操作系统的基本原理。
本书适合操作系统的初中级学习者阅读,适合通过大学课程和其他入门书对操作系统有所了解,但是对具体细节缺乏深入理解的读者,以及那些对操作系统的具体实现有兴趣的读者。
目录
第I部分
什么是UNIX V6 1
第1章 UNIX V6的全貌 2
1.1 什么是UNIX V6 2
1.2 UNIX的历史2
1.3 UNIX V6内核 4
1.4 构成UNIX V6运行环境的硬件 4
PDP-11 5
1.5 代码 9
1.6 手册 9
1.7 小结 10
第II部分
进程 11
第2章 进程 12
2.1 进程的概要 12
什么是进程 12
进程的并行执行 12
进程的执行状态 14
用户模式和内核模式 14
交换处理15
2.2 proc结构体和user结构体 15
proc结构体 16
user结构体 17
2.3 为进程分配的内存 21
代码段 21
数据段 21
虚拟地址空间 22
变换地址 24
2.4 小结 26
第3章 进程的管理I 27
3.1 进程的生命周期 27
3.2 创建进程 28
进程的复制 28
父进程和子进程 29
系统调用fork 29
newproc() 32
panic() 36
3.3 切换执行进程 37
中断执行进程 37
进程的执行状态 37
选择执行进程的算法 38
上下文切换 39
系统调用wait 39
sleep() 39
swtch() 41
swtch() 的返回位置 44
setpri() 51
wakeup() 51
setrun() 52
3.4 执行程序 53
程序执行文件的格式 53
系统调用exec 54
estabur() 62
sureg() 65
expand() 66
3.5 进程的终止 68
系统调用exit 69
系统调用wait 71
3.6 数据区域的扩展 73
系统调用break 73
3.7 管理内存和交换空间 76
map结构体 76
获取未使用区域 77
释放区域 79
3.8 小结 81
第4章 交换处理 82
4.1 什么是交换处理 82
代码段和数据段 82
sched() 83
xswap() 87
4.2 共享代码段的处理 88
xalloc() 90
xfree() 93
xccdec() 93
4.3 小结 94
第III 部分
中断 95
第5章 中断与陷入 96
5.1 什么是中断与陷入 96
什么是中断 96
什么是陷入 97
5.2 优先级与向量(Vector) 98
中断优先级和处理器优先级 98
中断和陷入向量 100
5.3 中断和陷入的处理流程 100
发生中断或陷入 101
执行call和trap 104
5.4 时钟中断处理函数 107
时钟设备的规格 107
时钟中断处理函数的内容 108
clock() 113
5.5 陷入处理函数 117
trap() 117
grow() 122
5.6 系统调用的处理流程 123
传递参数的方法 123
sysent结构体 124
trap() 126
5.7 小结 128
第6章 信号 129
6.1 什么是信号 129
信号的发送方法 129
确认接收信号 129
信号的种类 130
ssig() 131
kill() 132
signal() 133
psignal() 133
issig() 134
psig() 134
core() 136
在系统调用处理中处理信号 136
6.2 跟踪功能 137
什么是跟踪 137
ipc结构体 138
跟踪的处理流程 138
stop() 139
ptrace() 140
procxmt() 142
wait() 143
6.3 小结 144
第IV 部分
块I/O 系统 145
第7章 块设备子系统 146
7.1 设备的基础 146
设备的种类 146
设备驱动 146
类别和设备编号 147
特殊文件 147
7.2 块设备子系统 148
缓冲区
摘要与插图
【前言】本书针对1975年由贝尔实验室①发布的UNIX第6版(Sixth Edition Unix,此后简称为UNIX V6)的内核源代码进行解说。面向的读者主要是计算机专业的学生,以及从事计算机相关行业的具有初中级水平的技术人员。
考虑到一部分读者会有诸如“我对内核源代码根本不感兴趣”或者“与这种老古董相比,我喜欢更现代的操作系统”等看法,笔者想先阐述一下 阅读内核源代码的引人入胜之处,然后再解释 UNIX V6为何适合初次接触内核源代码的读者。
阅读内核源代码的意义
我们可以将操作系统(OS,Operating System)看做是一种软件(集合),它对包括硬件和软件在内的计算机系统的各个部分进行管理,并为用户提供便于使用的操作界面。 内核作为操作系统的核心部分,提供计算机系统必备的功能,因此也被称为狭义的操作系统。例如,shell之类的程序通常不是内核的一部分,而是利用内核提供的功能来实现的。内核以外的程序通常被称为用户空间(userland)程序,或用户程序。
通过阅读并理解内核源代码,我们会有如下收获。
对计算机系统的全貌有更深入的了解
掌握了作为计算机系统核心部分的内核,不仅对操作系统,对计算机的全貌也会有更为深入的认识。 对通过大学课程或其他途径学习的各种领域、各个层面的知识之间的关联性也会有更清晰的认识,让人有醍醐灌顶的感觉。
让操作计算机成为一种令人愉快的体验
理解了计算机系统的全貌,操作计算机本身也会变得更加令人愉快。比如,在计算机上执行某个程序的时候,如果能够准确把握系统内部所进行的操作,是不是一件很令人兴奋的事情呢?这种体验将加深读者对计算机的兴趣,使读者更有动力去提高自己的技术水平。
加深对知识的理解
阅读代码与否,对知识的理解程度会有云泥之差。如果只学习了概要,既 容易遗忘也难以应用。相反, 理解代码能够使你对学到的算法和思路举一反三,使之 成为可以受用一生的财富。
————
① 由美国的AT&T公司和Western Electric公司于1925年设立的研究开发机构。
提升技术人员自身的水平
作为计算机行业的技术人员,阅读并理解了内核源代码有助于在专业领域里将自己提升到一个新的层次。尽管在范围内这个领域的从业者不断增加,但是在了解应用层面的同时, 对操作系统等底层的知识也有所了解,并且能够对系统做出整体优化的技术人员,仍是凤毛麟角。
但是恰恰是具备这种素质的人,才能在第一线发挥不可替代的作用。 如果想拉大与竞争对手的差距,是必须理解系统内核的。
为何选择UNIX V6
接下来想说明一下为什么不选择的操作系统,而将历史比较悠久的UNIX V6 作为本书的题材。
代码行数约为1万行
UNIX V6 的内核源代码包括设备驱动程序在内 约有1 万行,这个数量的源代码,初学者是能够充分理解的。有一种说法是一个人所能理解的代码量上限为1 万行,UNIX V6的内核源代码从数量上看正好在这个范围之内。看到这里,大家是不是也有“如果只有1万行的话没准儿我也能学会”的想法呢?
另一方面,的操作系统,例如Linux 版的内核源代码据说超过了1000 万行①。就算不是初学者,想理解全部代码基本上也是不可能的。
充实的资料
UNIX V6 的用户手册、相关资料和论文 都可以在网上找到。运行UNIX V6 所需的处理装置PDP-11 以及周边设备的设计文档,很大一部分也可以检索到。
① 另外, 有一本关于UNIX V6 的指南已经问世多年。此书名为《莱昂氏UNIX 源代码分析》(Lions’ Commentary on UNIX,机械工业出