深入理解计算机系统 第 1 课 总览
本页目录
这门课是 CMU 的镇校神课,其课程编号 15213 也正是 CMU 的邮编,故有:不上 15213,等于没来过 CMU。课本 CSAPP 也是非常经典的计算机教材。虽然我之前大概看过一次,不过这次跟着 CSAPP 的作者一起,再学习一次。
第一节课主要是介绍课程的总体内容,给大家一个整体的认识。
小技巧
- Mac 下利用 lldb 来进行基本概念的试验,如:
$ print 50000 * 50000 - 利用 gdb 来阻止发送 bomblab 的结果到 server 中,这样就不会被扣分
大部分计算机学科的课程强调抽象,比如说抽象数据类型还有渐进分析。抽象很强大,但是也有其局限性,尤其是在出 bug 的时候。这时,我们就需要去理解这些抽象的底层实现。
上这门课可以让你成为一个更有效率的程序员——高效寻找和消除 bug,理解和调整程序的性能表现,更重要的是,这门课几乎是所有其他重要学科的先导课程:编译器,操作系统,网络,计算机架构,嵌入式系统,存储系统等等。
接下来会介绍五个必须知道的事实,不然很可能会因为理解不到位而无法找出问题所在。
Great Reality #1 Ints are not Integers, Floats are not Reals
Ints 不是整数,Floats 不是实数。这句话的意思是,因为计算机表现能力的限制,使得整型和浮点型和真实数学的表现有一些差异。
参考下图,举两个简单的例子:
- 一定成立吗?
- 对于浮点数来说,一定成立
- 对于整型来说,不一定,可能会有溢出的情况
- 可以通过 lldb 前两次的输出发现问题所在
- 一定成立吗?
- 对于无符号/有符号整型来说,一定成立
- 对于浮点数来说,不一定,可能会因为精度问题被舍入
- 可以通过 lldb 后两次输出发现问题所在

计算机运算虽然结果可能很奇怪,但绝不是随机数,所有的算术操作都有重要的数学性质。但是这种性质和我们日常生活中使用的数学性质有一些差异。造成这个现象主要的原因是精度表达的限制(32位,64位)。
对于 Integer 的操作,满足 rings 性质:Commutativity, Associativity, Distributivity。
对于 Float 的操作,满足 ordering 性质:Monotonicity, Signs
Great Reality #2 You've Got to Know Assembly
虽然我们不需要用汇编语言写程序,但是需要在机器执行那一级去理解汇编,例如:
- 高级语言模型崩溃,出现 bug 时,理解程序的行为
- 了解编译器所做的优化以及代码中比较低效的部分
- 编译器输出机器代码
- 操作系统必须管理进程状态
- 创造/对抗恶意软件时,x86 汇编是必须的
Great Reality #3 Memory Matters
Random Access Memory Is an Unphysical Abstraction
随机访问内存是一个非物理的抽象,实际上
- 内存不是没有边界的,需要进行分配和管理
- 内存引用 bug 很麻烦,因为可能导致在一段时间或者代码的不同位置出现问题
- 内存的性能不是平均的,缓存和虚拟内存可以极大影响性能,利用好内存系统的特性可以极大提高性能
C/C++ 没有提供任何内存保护机制,可能出现:
- 数组越界引用
- 非法的指针
- 滥用 malloc/free
这就容易导致非常恶心的 bug,因为我们没办法判断是程序本身的 bug,还是系统和编译器的 bug。一旦出现问题,其实根源很早就埋下,不容易发现。这时候可以怎么办呢?
- 用带保护机制的语言来写:Java, Ruby, Python, ML, ...
- 理解可能出现的问题
- 利用查找引用错误的工具(例如 Valgrind)
Great Reality #4 There's more to performance than asymptotic complexity
不要被所谓的大 O 计算忽悠了,复杂度比这个要复杂得多。即使是 O(1) 的部分,可能也是很重要的因素,哪怕可以数出来运算的数量,也无法预测性能表现。需要在多个层次进行优化:算法,数据表示,程序流程以及循环。
要做这些优化,就需要理解系统本身:程序是如何编译执行的,如何去衡量程序性能表现并且找出瓶颈,如何在不破坏代码模块性和通用性的前提下提高性能
Great Reality #5 Computers do more than execute programs
计算机不只是执行程序而已,还需要进行数据的传输,因此 IO 系统对于程序的稳定和性能都非常关键。在这个网络时代,有了更高的连接要求,根据不同的系统层次,有:
- 匿名进程的并行操作
- 从不可靠的介质复制(比方说 U 盘)
- 跨平台兼容性
- 复杂的性能问题
这门课是几乎所有计算机学科的基础课,整个学期有 7 个 lab 加上期中与期末考试。可以通过访问『shark machines』来进行试验,用 andrew id 登录
linux> ssh shark.ics.cs.cmu.edu
下面大致介绍下主要知识点和不同的 lab 的重点
Programs and Data
- 主题
- 位操作,数学计算,汇编程序
- C 控制流程的表示以及数据结构
- 体系架构和编译器
- 作业
- L1(datalab):操作 bits
- L2(bomblab):拆除一个二进制炸弹
- L3(attacklab):基本的代码注入攻击
The Memory Hierarchy
- 主题
- 内存技术,内存层级,缓存,磁盘,locality
- 体系架构和操作系统
- 作业
- L4(cachelab):做一个缓存模拟器并且进行优化,与此同时学习如何在程序中利用 locality
Exceptional Control Flow
- 主题
- 硬件异常,进程,进程控制,Unix 信号,非本地跳转(nonlocal jumps)
- 编译器,操作系统和提及架构
- 作业
- L5(tshlab):写一个自己的 Unix shell
Virtual Memory
- 主题
- 虚拟内存,地址翻译,动态存储分配
- 体系架构和操作系统
- 作业
- L6(malloclab):自己实现 malloc 功能,借此了解系统层次编程
Networking and Concurrency
- 主题
- 高层和底层 IO,网络编程
- Internet 服务,Web 服务器
- IO Multiplexing with select
- 网络,操作系统和体系架构
- 作业
- L7(proxylab):写一个 web proxy,借此学习网络编程和并行/同步
第一个课的内容大概是这么多,之后会跟着自己学习/课程进度来完成这个系列的文章。
相关文章
- 深入理解计算机系统 第 25 课 Thread-Level Parallelism2016-04-08
- 深入理解计算机系统 第 26 课 Future of Computing2016-04-08
- 深入理解计算机系统 第 27 课 总结2016-04-08
- 深入理解计算机系统 第 23 课 Synchronization - Basics2016-04-07