seegongsik
操作系统

什么是系统调用

上一课结尾,我们发现了一道奇怪的缝隙:操作系统给每个文件都定了权限,可我的程序连一个允许读取的文件,都没法直接从磁盘里取出来。其实,程序根本不能随意碰磁盘、屏幕和网络,它被关在一道结实的围栏里。那它又是怎么打开文件、把字显示到屏幕上的呢?

01

程序被关在围栏里(用户态)

前面讲过,操作系统筑起墙,不让程序互相侵占对方的内存。同样的墙也挡在硬件前面。普通程序不能直接伸手去碰磁盘,不能直接在屏幕上点亮一个点,也不能直接摆弄网络设备。
这种被关在围栏里的状态,叫作用户态。
看起来憋屈,却有道理。要是随便哪个程序都能直接摆弄硬件,一个错误百出或者心怀恶意的程序,就可能把整台电脑搞垮。

程序
磁盘

点按钮,程序就直接伸手去碰磁盘。中间的墙变红,把它挡了回来:处于用户态的程序不能直接触碰硬件。

每次直接伸手都会被挡住,从安全角度看理所当然。
可这就怪了。我们每天用的程序,明明能正常打开文件、显示照片、连上网络。既然被关着,这些事它是怎么办到的?
秘密在于:它不自己动手,而是去请求。

02

办法:到正式窗口去请求(系统调用)

去银行时,我们不会自己走进金库,而是在窗口递上一张申请单,由握着钥匙的职员替我们办理。
程序也是这样。它自己打不开磁盘,就到操作系统的窗口去请求:“帮我打开这个文件”“把这些字显示到屏幕上”“把这个通过网络发出去”。这样递给操作系统的每一个请求,都叫作系统调用。
关键在于,程序不自己干活,而是让操作系统去干,因为只有操作系统才有权碰硬件。

程序
→
操作系统窗口
→
磁盘

点按钮,程序(金色)就请操作系统窗口(蓝色)“打开文件”,操作系统替它到磁盘上办好,再把结果交回来(绿色)。程序自始至终没有直接碰到磁盘。

到窗口一请求,原本办不成的事就办成了。程序仍在围栏里,却借着操作系统这个代理人,办成了外面的事。
可有一点耐人寻味:同样一块磁盘,为什么程序去碰就被挡住,操作系统去碰就可以?
在越过窗口的那一瞬间,一定有什么切换了。

03

越过窗口,权限就切换(用户态 ↔ 内核态)

秘密在于,CPU 有两种模式。一种是我们的程序所在、能力受限的用户态;另一种是操作系统的内核态,在那里硬件和其他一切都碰得到。
程序平时在用户态里运行。系统调用越过窗口的那一刻,CPU 短暂切换到内核态。操作系统凭着这份强大的权限办好所请求的事,一办完就立即切回用户态,把结果交给程序。
强大的力量只在处理请求的那一刻、而且只通过这个窗口授予,随后马上收回。

用户态

点一次按钮,系统调用越过窗口,操作系统在内核态(蓝色)里处理请求;再点一次,就回到用户态(金色),拿到结果。

模式短暂切换、又切回来,这一趟短短的往返正是操作系统安全的核心。强大的力量不会一直开着,只在请求到来的那一刻打开,随即关上。
可还剩一个疑问:要是只要越过窗口,操作系统就照吩咐全都照办,那和程序直接碰硬件到底有什么区别?
所以窗口还有一件事要做:检查。

04

窗口只有一个,才能检查(权限确认)

要是操作系统一接到请求就不问不查、全部照办,窗口就只是一条过道。可操作系统不会这样做。
因为所有请求都必须经过这一个窗口,操作系统可以在动手之前先检查:“这个程序有权读这个文件吗?”上一课看到的权限确认,正是在这里进行的。
有权限就办理,没有就拒绝并返回错误。一个窄窄的窗口,就成了所有危险操作都必须经过的关卡。

从三个请求里选一个送到窗口。操作系统检查权限:读我的文件、输出到屏幕会被办理(绿色),写朋友的文件则被拒绝,并返回错误(红色)。

被允许的请求通过了,被禁止的请求在门口被拦下。窗口窄,并不是不方便,反而是一道安全装置。
既然所有危险操作都要经过同一个地方,规则只要在那一处守住就行。
现在,可以把用户态的围栏、作为请求的系统调用、短暂的内核态,以及窗口处的检查串成一条线了。

05

小结:串成一条线的往返,以及窗口背后的内核

把整个过程串成一条线,就是这样:程序在用户态的围栏里运行,碰不到硬件;需要什么,就通过系统调用到正式窗口去请求。
越过窗口的那一刻,CPU 短暂切换到内核态,操作系统先检查权限,再办理事情;办完后切回用户态,把结果交回去。
所以,系统调用就是连接程序与操作系统力量的唯一一道严密把守的门。打开文件、在屏幕上点亮一个点、往网上发送点什么,这一切都悄悄经过这道门。

按顺序点五个步骤,往返一圈就依次亮起:程序、系统调用、内核态与权限检查、处理事情、返回结果。五格全亮,一圈就走完了。

那么,在窗口背后,用内核态的强大力量真正把事情办好的,是谁?操作系统最深处的中心,握着全部权限、直接和硬件打交道的那一部分,有一个名字:内核。说到底,系统调用就是发给内核的请求。
下一课,我们终于要正面认识内核。到目前为止看到的调度、内存、文件、权限和窗口,究竟都在谁的手里运转,到时会在一处看清楚。

一句话总结程序被关在围栏里(用户态),不能直接碰硬件,要办事就得请求操作系统。这个请求就是系统调用,也就是把“打开这个文件”“显示到屏幕上”之类的要求递到正式窗口。越过窗口的那一刻,CPU 短暂切换到强大的权限(内核态),由操作系统把事办完,随即切回原来的模式。正因为窗口只有一个,操作系统能先检查每个请求(权限确认也在这里进行),于是围栏牢牢立着,程序仍能办成它需要的事。
← 操作系统
如果有帮助,请支持我们