30天制作操作系统第2天

30天制作操作系统第二天

这是一个菜鸡为了学习操作系统来练习写的操作系统,参照于书籍《30天自制操作系统》。
相关程序已经放到GitHub中,如果我的能力到位我可能会在这个操作系统的基础上进行添加及优化,作者已经把所有东西都做到极致了,我能做的很少,我只能把自己分析学习的文章总结出来。因为自己能力可能不到位,可能会有些错误希望大家理解,发到这里更多的原因的起到记录作用,如果以后的我回看我写的文章有错误,我会进行修改,同时也希望大家互相学习。
相关项目及源码已经放到GitHub中:https://github.com/Most3R-03/Simple-Operating-System

分析一下makefile文件以及输出的.sys .ipl.bin文件等
正常应该把启动系统和运行系统分开,启动系统只管启动并将磁盘文件加载到系统内存,运行系统可以修改并写入到磁盘文件中。
Ipl.bin为启动系统,由ipl.nas编译出来
Haribote.sys为运行系统,由haribote.nas编译出来(里面是真正要加载到内存并持续运行的系统)
Edimg.exe可以将ipl.bin+haribote.sys输出为启动系统和运行系统分开的映像文件。

所以算出运行系统内存的偏移就可以。在昨天为0xc200地址。
在这里插入图片描述
将硬盘里的系统加载到内存之后JMP到0xc200内存地址,运行系统
在这里插入图片描述

这是运行参数

现在我们来测试,首先将haribote.nas编译成haribote.sys 这里haribote.nas是设置显示器显示模式的。编译成启动系统。
make.bat haribote.sys
然后调用edimg创建镜像
Make.bat haribote.img 生成镜像
Make.bat run 运行镜像

达到了全黑效果!

书里所给的c语言编译器,只能生成32位的机器语言,所以我们选择用32位模式开发系统
16位模式启动调用AX和CX寄存器会非常方便,但是调用EAX和ECX等32位的寄存器会非常麻烦,所以16位的机器语言在32位模式下不能运行。

因为bios使用16位机器语言编写的,所以如果想让bios做一些事情,应该全开头让bios做。如果用c32位编译器生成之后就是32位程序了。

我们现在只用bios为我们获得键盘的状态,比如numlock是on还是off状态。
在这里插入图片描述
开始之我们先设置AL AH的值,调用INT10设置显示模式,
之后更改显示的参数,
再从bios获取指示灯的状态,放入LEDS内存(0x0ff1)中方便读取。
VRAM(0xa0000)指的是显卡内存,这一块的地址对应着画面上的像素,可以用这个机制绘制出图案来。
现在我们已经把画面的像素数 颜色书 以及键盘信息都保存起来到0x0ff0附近。
开始导入C语言。
在这里插入图片描述
我们进入HariMain函数之后进入fin循环,fin为goto的标签。
我们怎么让bootpack.c变成机器语言的呢?

首先,使用cc1.exe(c语言编译器)将bootpack.c生成bootpack.gas
第二部,使用gas2nask.exe(gas编译成nas格式)从bootpack.gas生成bootpack.nas
第三步,使用nask.exe从bootpack.nas生成bootpack.obj
第四步,使用obi2bim.exe从bootpack.obj生成bootpack.bim
最后,使用bim2hrb.exe从bootpack.bim生成bootpack.hrb
最后使用copy命令将asamhead.bin与bootpack.hrb结合起来就生成了haribote.sys

-nas并不能直接转换成sys文件,因为语言转换成机器语言需要有一部分汇编来写,然后再链接到c语言写的程序上

我们并没有让我们的系统处于HALT模式,非常的耗电,但是我们的c语言中没有HLT命令
所以我们需要用汇编语言来写一个c语言函数让c语言调用,名为io_hlt,我们在与bootpack.obj链接的时候把我们写的函数加上。因此将输出的格式设定为WCOFF模式,另外还要把他设定成32位机器语言模式,因为我们的程序是32位程序。
Nask目标文件的模式下,必须设定文件名信息,然后再写命下面程序的函数名。要在函数名前面加上_才能使之与C语言函数更好的链接。需要链接的函数名需要用GLOBAL指令声明。
在这里插入图片描述
我们用汇编语言写了一个供C语言程序调用的函数。
接下来我们修改用与调用io_hit的c程序bootpack.c
在这里插入图片描述
作者对makefile文件进行了修改
在这里插入图片描述
在这里插入图片描述
这是bat命令在将obj变成bim所参照的rule文件,同时可以将naskfunc.obj目标文件与bootpack.obj目标文件共同生成bootpack.bim,我们为了能让上面完整的机器语言实际使用,还要针对不同操作系统进行必要的加工,比如说加上识别文件头、压缩等

大致就是将步骤进行了简化,我们编译一下。
Make.bat naskfunc.obj 将naskfunc.nas生成obj目标文件
Make.bat bootpack.gas 将bootpack.c变成gas文件
Make.bat bootpack.nas 将bootpack.gas变成nas文件
Make.bat bootpack.obj 将bootpack.nas变成obj文件
Make.bat bootpack.bim 将bootpack.obj与naskfunc.obj共同链接成bim文件
Make.bat bootpack.hrb 将bootpack.bim变成hrb文件
Make.bat haribote.sys 将bootpack.sys与asmhead.bin结合生成haribote.sys
asmhead前身是haribote.nas(更名),他的功能是将bios信息放到内存中用于读取,然后对c语言的程序进行调用。
Make.bat haribote.img 将ipl10.bin与haribote.sys结合成hairbote.img镜像文件
ipl10.bin用于将磁盘读入内存中,并跳转到sys入口点,分开写是为了修改方便。

Make.bat run 调用qemu进行运行
在这里插入图片描述
运行成功,

但是我们想往VRAM里写点东西,所以我们选择用汇编语言再写一个往内存写数据的函数。我们来修改一下naskfunc.nas

在这里插入图片描述
32位系统函数调用参数是通过压栈调用的,参数入栈是从右往左开始入栈
Esp所指 Addr Date 栈底
低—高
Esp指向的是栈顶的一个空位置,因为写数据的时候是先写到栈上数据esp再加4的。

对于16位有些寄存器不能指定地址,32位来说所有寄存器都可以指定地址。

在这里插入图片描述
此外还增加了一行INSTRSET指令,用于告诉寄存器这是486的机器,机器便会将ECX解释成寄存器名不会解释成标签。

记得在汇编函数前声明global函数!

汇编部分准备好了,我们现在来改写c语言导入函数。
在这里插入图片描述
写完后编译,发现背景全白,写入成功!
在这里插入图片描述
在这里插入图片描述
还可以少变白几个。

同时可以添加条形图案。
在这里插入图片描述
在这里插入图片描述
内存中这样即可

内存中同样可以利用指针对内存赋值
Write_mem3(i,i&0x0f);
可以由
*i=i&0x0f;
代替,但是会出现类型错误,写法是正确的,当其翻译成汇编语言的时候是这样的:
Mov [0x1234],0x56
在指定内存的时候并没有说出数据类型,只有在另一方也是寄存器的时候才能省略。
MOV BYTE[0x1234],0x56
我们需要指定数据类型才可以,到底是BYTE WORD DWORD.
我们需要告诉计算机数据类型是byte
Char *p;//用于BYTE类地址,类似于AL的一字节变量
Short *p; //用于WORD类地址,类似于AX的2字节变量
Int *p; //用于DWORD类地址,类似于EAX的4字节变量

现在我们将代码改成指针赋值的形式
在这里插入图片描述
运行成功
在这里插入图片描述
如果将普通整数直接赋值给内存地址变量,就会有警告,为了避免这种情况的发生,我们可以改写成
P=(char *)i; //我们可以将i整数i强制转换成内存地址。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值