操作系统开发问题

现在还是人类 2011-11-18 12:22:19
加精
这段时间没事在自己写操作系统,其中遇到了很多问题,想和大家分享一下我研究的一点成果
以及讨论一下技术方案。
在我理解的操作系统,主要由 Bootloader + Kernel + Shell 所组成,目的是完成一个管理
计算机资源并提供相关接口开发应用程序的平台基础。

Bootloader:可以分为 Boot 程序和 Loader 两个程序所组成,也可以直接是一个程序完成,
但主要看 Kernel 架构和文件系统等选型决定是分两个程序还是一个程序完成工作。
其实 Bootloader 主要是计算机启动时自动加载到内存执行的第一个程序,也被称为引导程序,
它是运行在 CPU 的实时模式下的 16 位程序,而系统启动时只会加载 512 个字节,即一个扇区
的数据到内存执行,这也就限制了 Boot 程序或这说 Bootloader 程序编译后的大小不能超过
512 个字节,如果文件系统定义得不那么复杂,而且内核加载过程不需要特别初始化的话,这个程序
完全可以用 Bootloader 的方式一次加载内核(比如内核程序直接有汇编开发)。
但如果想实现 C/C++ 语言来开发内核,而编译器又是现有系统的编译器,这个 Bootloader 就得
分两个步骤来完成,先是 Boot 程序,功能是先加载 Loader 程序,然后由 Loader 程序初始化
好环境再加载 Kernel。

Kernel:这个所谓的内核,在我的理解就是提供了一堆预先写好的基础函数放到内存中共其他应用
程序调用。比如提供 OS_ReadFile、OS_LoadAPI 等函数,然后应用程序启动时可以通过特定的内存
地址找到这些函数的内核地址,从而用跳转指令调用这些函数。这些一系列的函数累加起来,实现
了系统所谓的内存管理、进程管理、线程管理、设备管理等等功能。然后 Kernel 的初始化及载入
过程完成后就可以把执行权移交给 Shell 与用户进行交互了。

Shell:在我的理解,Shell 就是人机交互的管理程序,如 DOS 下的命令行形式的人机交互方式,
或者是 Windows 下图形模式的人机交互方式,理论上说,这个 Shell 是系统执行的第一个“应用程序”,
理论上 Shell 里的过程基本上全是调用 Kernel 所提供的函数完成的。

到现在为止,对于写“操作系统”,我越来月不清晰,因为有以下几个顾虑。
1、开发环境
如编译器是自己写好还是用现成的好,如果用现成的,免不了要根据别的系统走开发路线,而且
也未必是能实现我想用 BASIC 开发系统的想法。但自己写编译器难度又较大。
2、内核的定制
如果用高级语言开发内核,还是与编译器有关,包括应用程序的执行问题,这个内核还是与编译器
息息相关,如果不考虑高级语言,用汇编来写,灵活性比较大,但如果要写大,代码管理也很叫人
头痛。而且最终的应用程序管理部分也会卡在可执行程序的格式定义上,因为将来的应用程序不可能
也全由汇编开发,这样就没什么价值了。
3、是否采用现有系统的模型
比如 Windows、Linux、MacOS、DOS、uCos、Menuet OS 等,都有自己的特点,自己定制方式是比较随意,
但相对来说所有东西都要自己做,就比如如果不用现有的文件系统格式,自己弄一个,可能会更方面,
但即使格式化和复制文件这种操作才最初的时候都要自己写一个程序去做这种事,然后才能调试效果。
但如果运用的现有系统架构,那今后的开发路线就是个模仿的过程,基本上还不如直接用那些系统来得
有意义。

目前在开发操作系统的时候,我采用了软盘上用的 FAT12 文件系统进行系统设计,主要是为了在 Windows
下方便管理文件。但发现这样很耗代码,因为 FAT12 文件系统大致分为4个部分:
1、BOOT 区域,就是引导用的第一个扇区,也就是所谓的 MRB 表。如果要保持标准的 FAT12 文件系统,
必须按照它的固有格式开发 Boot 程序,如:开始是3个字节的跳转指令,然后跟着 BPB 表信息,然后
才开始 Boot 程序的代码,最后就是 0xAA55 的引导结束符号,所以,这个 BOOT 程序实际上最多只有
448 个字节。
2、FAT 表区,这个 FAT 其实是 File Allocation Table 的缩写,主要是记录文件数据的族链信息,
只有在文件数据内容大于一个族(512字节)才会具体指向数据的逻辑族地址,如果文件数据内
容在512个字节内,是不会指向具体的数据所在逻辑扇区地址的。而且系统通常会备份一个FAT表,
这样即使有一个 FAT 表因为磁盘坏道不能正常读取文件数据起始地址,也有另外一个表可以顶上。
3、FDT 表区,这个 FDT 其实是 File Directory Table 的缩写,主要存放文件名、目录名或卷标等
信息,包括名称、属性、相关日期时间,数据起始扇区号、文件大小等,当文件大小小于或等于
512个字节时,其实没必要访问 FAT 表去读文件数据,因为 FDT 表已经有了数据起始扇区号的信息,
因为只有一个扇区数据,直接读那个扇区就好了。当文件数据超出一个扇区时,就需要依赖 FAT
表进行数据族链的查找了,只要在 FAT 表中搜索一个链头与 FDT 数据起始扇区号相同的就可以
按照循序访问到文件数据分布在那几个扇区号上。
4、数据区,也就是存储文件具体数据的地方,通常文件数据会以扇区为单位存储。如果文件较大,
可能产生一个文件存放数据分布在不连续的扇区上,如一个5个扇区数据的文件,他可能存储在
0x003 0x004 0x005 0x01E 0x01F 的地方,这时候就需要 FAT 的族链来找到这些数据的分布扇区
情况。

看到这里,可以想象,如果要根据这种方式找到指定文件,并把所有数据读出来需要的代码量肯定不小。
而且同时还要将运行模式初始化到 32 位系统的保护模式,并执行现型系统的可执行文件格式,那就更难
了。所以我采用 Boot 和 Loader 分开的模式,先加载稍微大点的 Loader 程序,然后再用 Loader 程序
处理这些更复杂的操作并加载内核。

但我这段时间还看了一些别的 OS 代码,发现, Kernel 部分如果不用现有系统编译器的程序编写,如果
直接用汇编写,整个初始化过程可以更简单,那个 Loader 程序其实就可以直接写成 Kernel 了。

我的想法是用 Basic 开发这个系统,本来的方案是这样,先写一个 BASIC 编译器,主要思路是写一堆
的汇编函数,模拟 Basic 的语法函数过程,然后分析 Basic 语法,把配合的语法用汇编替代,这样实现
Basic to Asm 的功能,然后再用汇编编译器编译程序。
这样即使使用的是 Basic 语言,其实出来的还是汇编的效果。不过因为全是调用封装的汇编函数,效率
肯定与直接用汇编根据情况编写代码要低一点。但起码实现了 Basic 开发系统的可能性。

但后来在运用 NASM 编译器时,发现 NASM 缺少些指令,如 cmps 等等,MASM 就没这种问题,但也存在
别的问题,所以我的代码该按照 NASM 的标准翻译还是 MASM 的标准翻译又成为了一个问题。后来就自己
去看了下 CPU 指令集相关的资料,发现历年来系统的发展、各种 CPU 指令系统的升级累加,从这方面入
手也不容易,比如 Inter 的 x86、Pentium 、MMX、CISC指令集等等等等,除了多还要考虑程序的兼容性
等等。感觉自己按照 CPU 指令集编写 basic 编译器写操作系统的想法越来越远。

相对来说,觉得用汇编写内核和应用程序要比用这种高级语言简单得多,但如果这样做下去,这个系统也
没什么价值。所以想大家给点方案,怎么去设计这个系统比较好。
如:用什么编译器?结构如何?文件系统有没有更好的方案?……
...全文
4448 121 打赏 收藏 转发到动态 举报
写回复
用AI写文章
121 条回复
切换为时间正序
请发表友善的回复…
发表回复
李照虎01 2013-08-05
  • 打赏
  • 举报
回复
楼主 我想学linux内核 有没有什么好的书推荐啊
happyyinzi 2013-07-29
  • 打赏
  • 举报
回复
king_2007 2013-07-29
  • 打赏
  • 举报
回复
楼主,我建议你用c语言编写编译器,这样做的好处就是为了将来在系统上用其他的高级语言编写程序提供一些兼容性,同时在为高级语言编写低层东西时提供一些封装的接口很有必要,在执行效率和开发效率,还有系统的安全性,还有系统的维护和扩展方面,c语言应该是个不错的选择,本人觉得,basic简单易开发,但是在可扩展性和执行效率、兼容性、安全性来说不是明智的选择,在编写内核方面,我建议,能用c语言开发就不要用汇编开发,汇编就是个执行速度,在考虑一致性和效率方面,你要拿捏好。 我看到,你想汇编编写像basic那样的编译器,我就觉得你对每个编程语言的语法风格不是了解,为什么c语言的有些功能,basic做不到呢?我觉得你应该好好想想,了解一下。为什么c语言不能取代汇编,或者说basic不能取代汇编语言呢?应该有它局限的地方,这不是一厢情愿的事情。祝愿楼主开发系统出来后,第一时间给我个源代码,我想学习,研究下。
u011532811 2013-07-29
  • 打赏
  • 举报
回复
俺不懂 俺也来顶一下
邹华 2013-07-27
  • 打赏
  • 举报
回复
看看 学习下
tornado_dai 2013-07-26
  • 打赏
  • 举报
回复
花盆花 2013-07-26
  • 打赏
  • 举报
回复
nb,我是新手,但我也特别想做一个操作系统玩玩,所以就研究了一下minix,感觉还挺好,写到shell了,虽然是模仿,但感觉挺好的,也从中学到了很多东西!
  • 打赏
  • 举报
回复
操作系统除了硬件抽象层要使用汇编外,其余部分都可以使用高级语言实现,而且大部分os内核也都是用c/c++实现的。你要自己写个编译器工作量不比写个os kernel小吧?。。。。。。。
LiangChenYingShi 2013-07-25
  • 打赏
  • 举报
回复
程序开发很难支持
BYSF_XF 2013-07-25
  • 打赏
  • 举报
回复
牛B,C语言没经验,汇编没学过,现在刚毕业搞.net应用层开发的路过。
Zimmerk 2013-07-25
  • 打赏
  • 举报
回复
其实WINDOWS也是在UNIX基础上构建起来的
孤影品茗 2013-07-24
  • 打赏
  • 举报
回复
不明觉厉,楼主要是单人开发的话,感觉时间上和精力上的投入会过于庞大,不过后续如果有众人的加入,前景还不得而知呢
songzhao85 2013-07-22
  • 打赏
  • 举报
回复
想知道楼主还在吗,2年没见了。
wangsufu77 2013-07-22
  • 打赏
  • 举报
回复
lanlongyun 2013-07-21
  • 打赏
  • 举报
回复
楼主,,,强悍!
才女凤姐 2013-07-21
  • 打赏
  • 举报
回复
不错。 群主辛苦了
无聊找乐 2013-07-20
  • 打赏
  • 举报
回复
两年前的帖子居然被翻出来. 不过看当时的楼主对所谓"程序"和"编译器"的理解不太正确,貌似走入歧途了. 不知道现在楼主做的怎样了.
mbugaifc 2013-07-20
  • 打赏
  • 举报
回复
xiaominx 2013-07-19
  • 打赏
  • 举报
回复
儿女情长 2013-07-19
  • 打赏
  • 举报
回复
不了解。 我想问一下,是不是每种操作系统都有它自己的各种编译器?(或者比如说c语言是不是需要分别实现windows、linux系统的编译器?)如果是,那你需要的编译器就不该用现有的。 当然,先模仿or借鉴一下别人的系统也是可以的。
加载更多回复(90)

1,066

社区成员

发帖
与我相关
我的任务
社区描述
VB 资源
社区管理员
  • 资源
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧