编译后的程序如何与操作系统交互?

26

当一个程序被编译时,它会被转换成机器码(machine code),这种代码可以被计算机“理解”。那么,这些机器码如何与操作系统进行交互以完成例如从键盘获取输入的操作呢?对我来说,机器码应该运行在比操作系统更低的级别,因此,我无法理解操作系统是如何作为编译后应用程序和硬件之间的中介进行操作的。

附注:我刚开始学习C++编程,并且正试图理解cin和cout的工作原理。


1
编译后的应用程序只需调用 DLL(操作系统中的 kernel32.dll 等)中包含的其他机器代码函数。那些其他机器代码是专门为与硬件配合工作而编写的,因此您不必担心这个问题。 - Seth Carnegie
1
这可能与您的问题略有偏离,不是真正的答案,但如果您对语言和操作系统之间的边界感兴趣,这可能会让您对过程中的许多步骤感到敬畏/恐惧/厌恶... :-/ http://stackoverflow.com/a/2444508/211160 - HostileFork says dont trust SE
2个回答

29

这是一个非常好的问题(比你知道的更好),有很多可以学习的。很多。

我会尝试简短地回答。操作系统充当软件和硬件之间的抽象层:

   Software
       .
      /|\    
       |   communicates with
      \|/
       '
Operating System
       .
      /|\    
       |   communicates with
      \|/
       '
   Hardware
操作系统通过称为“驱动程序”的程序与硬件进行通信(广泛使用的术语),并通过称为“系统调用”的过程与软件进行通信(不太常用的术语)。
实质上,当您进行系统调用时,您正在离开您的程序并进入操作系统的代码。系统调用是程序员允许与资源通信的唯一方式。
现在我会停在这里,但您还说:
对我来说,似乎机器码应该在操作系统以下运行,因此,我无法理解操作系统如何在已编译的应用程序和硬件之间充当中介。
这有点棘手,但一旦您了解了一些基础知识,就很简单。
首先,所有代码都只是在CPU上运行的机器码。没有代码比其他代码更高或更低(除了一些只能在特权内核模式下运行的命令)。因此,问题是,即使它放弃对CPU的控制,操作系统怎么可能控制呢?
当代码在CPU上运行时,存在一个称为“中断”的概念。这是发送到CPU的信号,导致当前正在运行的代码停止并切换到另一段代码,称为“中断处理程序”。
中断的示例包括键盘,鼠标和最重要的是时钟。
时钟中断定期引发,导致操作系统的时钟中断处理程序运行。在此时钟中断处理程序中,是操作系统的代码,检查当前正在运行的代码确定下一个需要运行的代码。这可以是更多的操作系统代码或更多的用户代码。
由于时钟始终在滴答作响,并且因为操作系统始终有这种周期性的机会在CPU上运行,它能够协调计算机内的一切,即使它使用与任何正常程序相同的一组CPU命令运行。

2
CPU可以在多种模式下运行(内核和用户),操作系统代码在更高特权的内核模式下运行。 - OrangeDog
谢谢,那是一个非常好的回答。只是为了明确,可以说系统调用就像是一种中断,它会停止应用程序代码的执行并将其切换到操作系统代码(即开始执行操作系统代码)吗? - mahela007
@mahela007 并不总是有中断的。正如OrangeDog所提到的,中断是一种告诉内核进入内核模式的方法之一。然而,这些与硬件中断略有不同。它被称为内核陷阱,是一种软件中断。请参见此处:http://en.wikipedia.org/wiki/System_call#Typical_implementations 和 http://en.wikipedia.org/wiki/Trap_%28computing%29。 - Geoff Montee
非常好的解释。但是,你能不能澄清一件事。如果用户代码和操作系统代码都在轮流运行,那么谁阻止用户代码直接访问硬件? - Rahul Bansal
@RahulBansal,OrangeDog已经在他的评论中解释过了。CPU可以以多种模式运行,具有不同的权限。 - riwalk

5
操作系统提供系统调用,程序可以调用它们来访问低级别服务。
请注意,系统调用与您可能用于执行外部程序的system()函数不同。
系统调用用于访问文件、通过网络通信、请求堆内存等操作。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接