如何在旧的桌面电脑上构build一个小型操作系统?

这可能是徒劳的,因为我知道编写一个操作系统是非常复杂的(尤其是自己)。

  • 我不期望构build下一个Linux或Windows。

  • 我知道这将是可怕的,越野车,并将无法正常工作,但没关系。

我想自己写一切,在大会C ,和(一些) C + +

这是一个未来的项目,因为我现在正在忙于其他一些事情,并没有立即有时间,但我想我现在会问,所以也许我可以得到很多答案,它可以build立并成为这种方法的一个有用的资源(我所看到的其他一切都涉及到使用minix,使用现有的引导程序,在虚拟引导程序中构build它等)。

我想用显示器,键盘和鼠标设置我的旧桌面之一,并开始在一个空白的硬盘驱动器上工作。

我想学习如何编写自己的bootloader(我已经find了很多关于这方面的资源,但为了完整性,请添加一些好的资源),我自己的USB驱动程序(如果有必要的话),CD驱动程序(如果这是必要的)等一切,从头开始。

  • 如何将代码放到电脑上? 最好用软盘来做吗? 大多数计算机是否可以通过USB棒进行操作?

  • 我需要什么样的驱动程序?你能提出一些build议吗?

  • 启动序列后 – 那么是什么? 如何进入保护模式等

  • 如何在没有操作系统的帮助下pipe理内存? 我只是使用任何我想要的地址? 不需要初始化?

  • 我无疑会遇到什么会迷惑我吗?

  • 我怎样才能使它不是一个命令行O / S,而是一个graphics?

  • 什么是build立在graphics操作系统上? 比如,我该如何做一些事情,如命令行,字体和顶部的图片?

  • 我在哪里可以阅读有关设置多任务环境? (即,有两个graphics式的命令行并排运行)。

  • 我将如何build立一种窗口系统? 一旦设置简单的多任务处理,如何在屏幕上显示graphics?

相信我,我明白这是一个非常复杂的项目,我可能永远不会完成它或任何使用它写任何东西。

还有很多其他的东西,我没有提到,如果你想到的话,也可以随意添加。

请为每个答案放上一个“主题”,例如,USB驱动程序,然后可能是资源列表,要注意的东西等等。

此外,请不要build议build立另一个操作系统或预先存在的代码。 我知道我会很多预先存在的代码(比如linux内核,示例资源,现有的驱动程序等等),但是最终我想自己写所有的代码。 我知道我应该从别的东西上来,而且还有很多其他的问题,如果我改变主意,走上这条路,我就能读懂。 但是这一切都是关于从头开始整个事情。

更新

我有很多很好的答案,主要是关于引导过程,文件系统和各种现有的项目,以供参考。

有关如何获得graphics的任何build议? 不同的video模式,以及如何与他们合作等?

首先要做的事情 读,读,读,读,读。 在希望实现自己的操作系统之前,您需要对操作系统的工作原理有一个明确的理解。

拿起Andrew Tanenbaum关于操作系统的书籍之一。 这是我们在大学的操作系统课上使用的一个:

现代操作系统http://ecx.images-amazon.comhttp://img.dovov.comI/51DptFJH9NL._SL500_AA240_.jpg

亚马逊上的现代操作系统

尽pipe可笑的封面,这是一个神奇的阅读,尤其是一本教科书。 Tanenbaum真的是这方面的专家,他对操作系统如何在引擎盖下工作的解释清楚易懂。 这本书大多是理论,但我相信他也有一本书,讨论更多的实施。 我从来没有读过,所以我不能评论它。

这应该可以帮助你理解进程pipe理,内存pipe理,文件系统以及你的操作系统内核需要做的所有事情,以使其达到可启动状态。 从这一点上来说,基本上就是为需要支持的硬件编写设备驱动程序,并提供C库函数的实现,以便进行内核调用,如打开文件和设备,读取和写入,在进程之间传递消息等。

请阅读x86程序集(假设您正在为x86机器devise此程序)。 这应该回答你在处理器工作模式之间移动的许多问题。

如果您有任何电子方面的知识,从编写具有充足文档的embedded式设备的操作系统开始,可能会更容易,因为它通常比x86 PC更简单。 我也一直想写我自己的操作系统,我开始为D​​igilent的这个开发板编写一个微内核embedded式操作系统。 它可以运行赛灵思公司的软核MicroBlaze处理器,该处理器具有非常全面的文档。 它也有一些内存,闪存数据存储,LED指示灯,开关,button,VGA输出等。大量的东西来玩耍,编写简单的驱动程序。

embedded式设备的好处之一还在于您可以避免长时间写入VGA驱动程序。 在我的情况下,Digilent开发板有一个板载的UART,所以我可以有效地使用串行输出作为我的控制台来获取整个事情,并以最小的麻烦引导到命令行。

只要确保你select的目标有一个容易获得和经过充分testing的编译器。 你不想同时编写一个操作系统和一个编译器。

http://www.osdev.org/和http://www.osdever.net/

欢迎来到OS开发世界。

请参阅SO的x86 标记wiki中的其他x86文档链接:Intel和AMD手册,编译器/汇编程序文档以及各种指南。

它还build议使用BOCHS或其他虚拟环境进行debugging,因为您可以单步执行引导加载程序并检查寄存器。

我build议至less在开始的时候,在Bochs或其他虚拟机上工作,原因是你可以随身携带它,它更容易debugging(你可以看到硬件的确切状态),如果你需要外部帮助debugging,他们可以使用与您完全相同的“硬件”。

我最有用的build议是让自己进入一个可以尽可能快地运行C代码的状态 – 例如启动,设置描述符表,并让自己的安全点运行编译的C.如果不是所有的内核都应该在C中,如果你想保持健全并继续工作。 大会虽然在某些地方是需要的,但却很乏味,往往难以debugging。

在最低级别上,操作系统需要做的最低要求是以某种方式驱动系统的硬件,并以某种方式加载执行某种“用户代码”。 如果你打算从PC开始,那么你需要编写可以从某个设备或另一个设备加载的代码。 旧的电脑有一个BIOS固件,它决定了硬件如何进行一些初始化(至less是video,键盘和某种forms的存储或引导加载程序)。 (2017年10月更新:较新的PC具有EFI或UEFI固件…这在很大程度上是一个迂腐的差异;服务与本讨论的目的相同)。

因此,首先要了解如何在目标系统上使用BIOS或其他固件的低级别细节。 也就是说,学习如何编写BIOS可以加载和执行的程序。 这将最终变成你的启动加载器。 从小开始。 直接从固件启动过程(在软盘上,或USB闪存盘上,将是一个好的开始……或在硬盘驱动器上,如果你喜欢的话)下载一个打印出来的程序:“Hello,Linus”。

从那里我build议写一个非常简单的串行驱动程序…更新您的启动加载程序初始化一些串行端口,并从那里开始下载。 然后它可以执行它所传递的代码。 从那里写了一些bootstrap,可以写入另一组块(我们还没有实现一个文件系统,甚至没有分区表parsing;所以我们只处理磁盘上的块的原始范围)。

在这一点上,你的引导加载程序应该能够通过串行线拉新的代码,将其转储到一个分区(是的,实现某种类的分区表处理…是否符合标准的PC约定在这一点上取决于你),并执行它。

从那里你应该可以在更复杂的function上工作。 从这个基地,你可以编写和编译一个新的“内核”…重新启动你的testing平台,并部署新的内核。

(你的引导加载程序应该采取一些信号,比如串口握手线上的BREAK作为跳过下载的命令,只是引导现有的映像;而且它也应该以这种方式处理一些超时。

从那里写一个非常简单的terminal层和命令shell? 一个文件系统? 实施命令来下载除内核以外的新的可执行内容(某种types的文件或对象)。 等等。

当然,你可以使用PC键盘和video(如果我正确记得,分别是BIOS INT 0x16h和INT 0x10H的东西)开始使用控制台驱动程序。 不过,我build议从一个串行驱动程序开始,因为您可以从任何其他现有(function)系统自动化构build/部署/testing循环。 由于你的新操作系统将作为一个交叉编译的项目开始,所以对你来说,处理这个问题的方法是非常重要的。

我不知道你想把你的项目做多远。 一个令人印象深刻的目标是实现“自我托pipe”。 如果你可以创build一个简单的汇编/编译器,可以让你使用你的新操作系统(重新)build立,链接,并启动到新的操作系统的工作版本…那么你已经实现了这一目标。 (注意这不是必须的,许多embedded式系统永远不会自行托pipe,而且没有任何问题)。

如果你不介意使用硬件虚拟化,那么有一门课程(书+讲座+软件),将把你从“从Nand到俄罗斯方块”。 你完全由你自己创build一个完整的计算机系统(为了这些目的primefaces的,给定的)电子NAND门,直到构build操作系统,一种语言,最后在个人机器上编写一个简单的游戏。

我认为这是一个好主意,而且我很快就会陷入困境。 这本书是惊人的便宜,我相信这门课在麻省理工学院教授。 我可以想象,没有比从头开始build立起来的整个系统的完整知识更好的感觉。

链接: http : //www1.idc.ac.il/tecs/

我会从小开始购买一个8086embedded式开发套件,并开发一个多任务操作系统。 一旦你拥有一个内核并熟悉在硬件层面的工作,你将会做好一些更具挑战性的工作。

build立一个VGA显示器的DOS克隆是一个相当具有挑战性的事情。 细节是巨大的。 🙂

具体的话题。

如何将代码放到电脑上? 最好用软盘来做吗? 大多数计算机是否可以通过USB棒进行操作?

BIOS将执行初级引导。


我需要什么样的驱动程序?你能提出一些build议吗?

任何不是直接的cpu /内存操作。 任何不是直接在CPU参考手册中。


启动序列后 – 那么是什么? 如何进入保护模式等

保护模式将成为启动序列的一部分。

那么你开始多任务处理,并找出如何启动进程。


如何在没有操作系统的帮助下pipe理内存? 我只是使用任何我想要的地址? 不需要初始化?

正确。 您可能最终需要整理一个虚拟内存系统。


我无疑会遇到什么会迷惑我?

没有debugging工具,没有IO


我怎样才能使它不是一个命令行O / S,而是一个graphics?

带着悲伤。 查找Windows 3.1和Linux,特别是X窗口。


什么是基于graphics的操作系统? 比如,我该如何做一些事情,如命令行,字体和顶部的图片?

查找X窗口。


最后的build议:学习linux / x windows。 这并不完美,但它提供了一种方法的理解。 还研究embedded式系统。

操作系统开发系列 @ BrokenThorn可能会让你感兴趣。

我看到很多对OS开发网站的很好的参考,所以我将介绍一种不同的方法:

如果你想从裸机上实现操作系统的经验,有一种比旧的PC更好的硬件select。 使用PC架构,您将花费过多的时间来编写30年devise历史中无趣的工件。 例如,项目的bootloader部分可能已经烧毁了很多勇敢的程序员。

例如,您将需要一组驱动程序来从磁盘和/或networking读取您的内核。 那么你需要代码才能进入保护模式。 那时候,你需要另外一套司机! 在这一点之后,将芯片切换到保护模式所做的工作极less。 你想在不同的PC上运行它 – 4年,你需要另外一组驱动程序。

研究引导ARM或其他32位“embedded式”芯片。 廉价的开发板是可用的,或者你可以焊接自己的! 有些内置以太网和USB。 我认为你会有更多的乐趣在一个健全的,非硬壳的build筑上工作,也许最终会有一些可重用的技能。

最重要的是,如果你想要在真正的硬件上运行,你绝对需要你的处理器手册的副本。 英特尔手册( http://www.intel.com/products/processor/manuals/ )是非常宝贵的。 他们从开关模式(真实/受保护)到虚拟内存pipe理(如果您select走得太远),进行系统调用(如果您曾经进入用户模式),都会重新开始。 最重要的是,他们非常详细地解释了一些必须设置的function的东西,比如TSS和段寄存器,大多数操作系统文本都没有讨论,因为它们更关心更高层次的概念,具体细节。

尝试阅读一个小的,基本的开源操作系统,如MikeOS的代码。

或者,我build议以下步骤(应该很有趣!):

  1. 写一个虚拟机。 定义你所有的处理器指令,以便你了解你的系统。 将其与SDL接口用于键盘,鼠标,屏幕,audio访问。 保持简单,这样你就可以立刻把所有的东西都放在头上。 它不需要成为最先进的虚拟机,只需要模拟“真实”计算机的function即可。
  2. 为您的虚拟机的处理器编写一个汇编程序。 请记住,这个汇编程序不一定是用虚拟机语言编写的程序,而是任何能够将汇编语言转换为机器代码的程序。
  3. 定义一个可执行的格式,并写一个简单的链接器。
  4. 你已经有了所有的部件来编写你的操作系统了! 用汇编语言编写,汇编……等等。你不需要这么复杂的启动加载过程,只需让你的机器先运行你的操作系统即可。

上面的步骤似乎有点愚蠢的写一个简单的操作系统,但嘿,这该死的乐趣。

你有一个雄心勃勃的目标。 但执行是关键。

大多数结构化方法(教科书或大学课程)将引导您完成整个过程,但是它们提供了许多细致的代码,掩盖了所选平台的奥秘细节,让您专注于大局观点:进程调度,内存pipe理,防止死锁,I / O等等。

我的build议是:切断你的期望,从一个基本的问题开始。

什么是操作系统?

计算机科学家(希望)从不会说操作系统是graphics用户界面,networking浏览器或连接USB设备的方式,或者用户实际上可以看到或触摸的任何东西。 相反,最基本的操作系统就是我上面提到的那些东西。 他们都属于一个大的资源pipe理伞。

操作系统不过是一个pipe理计算机硬件资源的程序:内存,CPU和外围设备。

下面是一个简单的操作系统:一个程序让用户使用串行连接键入程序(hex或二进制)。 一旦程序被input,程序就会运行。 程序结束后,控制权返回给用户,他们可以再次运行程序或键入新的程序。

在一个“干净”的架构上做这个工作,例如内存为64K的embedded式ARM处理器。 您可以在了解ARM的基本function后几天内汇编代码。 瞧! ,你已经有了一个操作系统。

它做一切操作系统应该做的事情:

  • 它通过不让用户覆盖操作系统来pipe理内存。
  • 它安排一个进程运行。
  • 它处理单个串行外设的I / O。

这给你一个构build块从开始。 你现在有很多select。 也许其中之一就是允许两个程序加载到内存中,让用户决定下一个要运行的程序。

或者你可以让用户暂停执行一个程序,切换到另一个程序,挂起并切换回去。 这是最基本的多任务,即使它是完全手动的。

你的select是无限的,但每一个都是从你以前的宝贝一步。

如果你不把眼光放得太高,这很有趣!

检查出MikeOS 。 它的一个相当简单的操作系统是可读的(如注释)程序集。 即使它相当简单,它有一个GUI,并支持一些networking和多媒体。

编辑 : MenuetOS是graphics。 它也是直接的,但比MikeOS更复杂

我在StackOverflow上维护一个资源列表: 如何开始操作系统开发 。 当你开始冒险时,请添加新的资源(即将开始:))

许多学校都有操作系统课程,可以完成你描述的很多东西。 我的学校(CMU)在C中教授操作系统,我们编写了一个内核,文件系统和shell,并提供了引导加载程序的代码。

不幸的是,我无法在网上find这个课程的确切资源(15-412),并且随着时间的推移而演变。 但也许人们可以在网上有很好的资源的学校发布链接。

您可能会喜欢这个名为“滚动您自己的玩具UNIX克隆操作系统”的教程,它非常有洞察力,应该可以帮助您。

祝你好运。

研究A2系统 (以前称为Oberon系统 )的想法,你可以偷。 这是一个由两个人build立的graphics操作系统,虽然公认是Niklaus Wirth。 首先在1990年左右发布,速度惊人的好。 Gutknecht有一本书。

理解系统编程概念是一个基本要求,可以深入了解操作系统linux * BSD和GNU / Linux的 F / OSS内核内部,尤其是早期版本可能有点更多的文件。 替代文字http://ecx.images-amazon.comhttp://img.dovov.comI/51zezQiqYYL._SL500_AA240_.jpg 替代文字http://ecx.images-amazon.comhttp://img.dovov.comI/51NEmsW4TCL._SL500_AA240_.jpg

关于低级graphics编程,这会给你很多信息: http : //www.osdever.net/FreeVGA/home.htm 。 (对于文本模式也非常有趣)

我无疑会遇到什么会迷惑我?

你会意识到,在PC上有很多东西是不清楚的:x86指令集本身是复杂的,当你直接访问硬件时,可能需要相当长的时间才能理解如何在屏幕上编写单个字符。

不要担心软盘等问题,大部分时间你都会使用Bochs或QEmu等仿真器。

看看Minix 。 研究源代码以及“ 操作系统devise和实现 ”。 考虑为项目做出贡献。 我认为Minix是一个非常好的和有希望的操作系统。 这也是资金充足的项目。 这意味着,你甚至可以得到你的贡献的报酬!

这很容易,因为BIOS已经内置了许多input/输出function,用于改变屏幕模式,改变像素颜色,将文本写入屏幕等等。 但是,它不包括对文件系统的支持,这是您必须在您的操作系统中纳入的less数几件事之一。

BIOS加载硬盘驱动器上的第一个扇区,并从那里开始执行代码,因此必须将第一个指令放在硬盘驱动器的第一个扇区中。

这个维基百科文章应该让你开始在BIOS中断写入文本到屏幕上,从键盘和其他东西接收键。 https://en.wikipedia.org/wiki/BIOS_interrupt_call

即使您打算使用c ++,我也强烈build议您阅读汇编编程,因为了解硬件的工作原理至关重要。