最简操作系统内核HelloOS

文章目录

  • 最简操作系统内核HelloOS
  • 1.Hello OS的引导流程
  • 2.HelloOS的引导汇编代码
  • 3.HelloOS的主函数
  • 4.控制计算机屏幕
  • 5.编译和安装
  • 6.操作过程图解
    • 6.1下载源码后解压
    • 6.2打开终端,执行命令make -f Makefile
    • 6.3将生成的HelloOS.bin文件拷贝到/boot文件夹下
    • 6.4在/boot/grub/grub.cfg中添加menuentry
    • 6.5进入GRUB引导界面,运行HelloOS

源码下载:HelloOS.zip-OS文档类资源-CSDN文库

运行环境:VMware+Ubuntu20(虚拟机的安装和配置问题请参考:VMware虚拟机安装 Linux(Ubuntu)教程_一顿吃不饱的博客-CSDN博客)

Hello OS的引导程序用的是GRUB(多重操作系统启动管理器),当Ubuntu安装好以后,GRUB就已经存在了。

1.Hello OS的引导流程

​ 简单解释一下,PC 机 BIOS 固件是固化在 PC 机主板上的 ROM 芯片中的,掉电也能保存,PC 机上电后的第一条指令就是 BIOS 固件中的,它负责检测和初始化 CPU、内存及主板平台,然后加载引导设备(大概率是硬盘)中的第一个扇区数据,到 0x7c00 地址开始的内存空间,再接着跳转到 0x7c00 处执行指令,在我们这里的情况下就是 GRUB 引导程序。

2.HelloOS的引导汇编代码

​ c是高级语言,它不能直接操作特定的硬件,所以我们用汇编代码处理c语言的工作环境。

MBT_HDR_FLAGS EQU 0x00010003
MBT_HDR_MAGIC EQU 0x1BADB002 ;多引导协议头魔数
MBT_HDR2_MAGIC EQU 0xe85250d6 ;第二版多引导协议头魔数
global _start ;导出_start符号
extern main ;导入外部的main函数符号
[section .start.text] ;定义.start.text代码节
[bits 32] ;汇编成32位代码
_start:
jmp _entry
ALIGN 8
mbt_hdr:
dd MBT_HDR_MAGIC
dd MBT_HDR_FLAGS
dd -(MBT_HDR_MAGIC+MBT_HDR_FLAGS)
dd mbt_hdr
dd _start
dd 0
dd 0
dd _entry
;以上是GRUB所需要的头
ALIGN 8
mbt2_hdr:
DD MBT_HDR2_MAGIC
DD 0
DD mbt2_hdr_end - mbt2_hdr
DD -(MBT_HDR2_MAGIC + 0 + (mbt2_hdr_end - mbt2_hdr))
DW 2, 0
DD 24
DD mbt2_hdr
DD _start
DD 0
DD 0
DW 3, 0
DD 12
DD _entry
DD 0
DW 0, 0
DD 8
mbt2_hdr_end:
;以上是GRUB2所需要的头
;包含两个头是为了同时兼容GRUB、GRUB2
ALIGN 8
_entry:
;关中断
cli
;关不可屏蔽中断
in al, 0x70
or al, 0x80
out 0x70,al
;重新加载GDT
lgdt [GDT_PTR]
jmp dword 0x8 :_32bits_mode
_32bits_mode:
;下面初始化C语言可能会用到的寄存器
mov ax, 0x10
mov ds, ax
mov ss, ax
mov es, ax
mov fs, ax
mov gs, ax
xor eax,eax
xor ebx,ebx
xor ecx,ecx
xor edx,edx
xor edi,edi
xor esi,esi
xor ebp,ebp
xor esp,esp
;初始化栈,C语言需要栈才能工作
mov esp,0x9000
;调用C语言函数main
call main
;让CPU停止执行指令
halt_step:
halt
jmp halt_step
GDT_START:
knull_dsc: dq 0
kcode_dsc: dq 0x00cf9e000000ffff
kdata_dsc: dq 0x00cf92000000ffff
k16cd_dsc: dq 0x00009e000000ffff
k16da_dsc: dq 0x000092000000ffff
GDT_END:
GDT_PTR:
GDTLEN dw GDT_END-GDT_START-1
GDTBASE dd GDT_START

以上的汇编代码分为 4 个部分:

  1. 代码 1~40 行,用汇编定义的 GRUB 的多引导协议头,其实就是一定格式的数据,我们的 Hello OS 是用 GRUB 引导的,当然要遵循 GRUB 的多引导协议标准,让 GRUB 能识别我们的 Hello OS。之所以有两个引导头,是为了兼容 GRUB1 和 GRUB2。
  2. 代码 44~52 行,关掉中断,设定 CPU 的工作模式。
  3. 代码 54~73 行,初始化 CPU 的寄存器和 C 语言的运行环境。
  4. 代码 78~87 行,GDT_START 开始的,是 CPU 工作模式所需要的数据。

3.HelloOS的主函数

#include "vgastr.h"
void main()
{printf("Hello OS!");return;
}

4.控制计算机屏幕

void _strwrite(char* string)
{char* p_strdst = (char*)(0xb8000);//指向显存的开始地址while (*string){*p_strdst = *string++;p_strdst += 2;}return;
}void printf(char* fmt, ...)
{_strwrite(fmt);return;
}

​ printf 函数直接调用了 _strwrite 函数,而 _strwrite 函数正是将字符串里每个字符依次定入到 0xb8000 地址开始的显存中,而 p_strdst 每次加 2,这也是为了跳过字符的颜色信息的空间。

5.编译和安装

Hello OS 的编译过程

​ 经过上述流程,我们就会得到 Hello OS.bin 文件,但是我们还要让 GRUB 能够找到它,才能在计算机启动时加载它。这个过程我们称为安装,不过这里没有写安装程序,得我们手动来做。

HelloOS的启动项

menuentry 'HelloOS' {insmod part_msdos #GRUB加载分区模块识别分区insmod ext2 #GRUB加载ext文件系统模块识别ext文件系统set root='hd0,msdos4' #注意boot目录挂载的分区,这是我机器上的情况multiboot2 /boot/HelloOS.bin #GRUB以multiboot2协议加载HelloOS.binboot #GRUB启动HelloOS.bin
}

​ 把上面启动项的代码插入到你的 Linux 机器上的 /boot/grub/grub.cfg 文件末尾,然后把 Hello OS.bin 文件复制到 /boot/ 目录下,一定注意这里是追加不是覆盖。最后重启计算机,你就可以看到 Hello OS 的启动选项了。

6.操作过程图解

6.1下载源码后解压

6.2打开终端,执行命令make -f Makefile

6.3将生成的HelloOS.bin文件拷贝到/boot文件夹下

执行命令

sudo mv HelloOS.bin /boot

这个过程需要输入密码

6.4在/boot/grub/grub.cfg中添加menuentry

执行命令

sudo gedit /boot/grub/grub.cfg

**注意:**添加的时候要根据自己的虚拟机情况修改代码

那么如何查看boot目录的挂载分区呢?

请参考链接:Linux如何查看boot目录的挂载分区呢_一顿吃不饱的博客-CSDN博客

6.5进入GRUB引导界面,运行HelloOS

如何进入GRUB引导界面?

重启虚拟机的时候长按esc键

成功运行最简操作系统HelloOS

最简操作系统内核HelloOS相关推荐

  1. 操作系统内核框架图整理

    Android框架: IOS框架(简): web_os框架: windows NT框架: Minix3框架: linux框架(简): Solaris框架: GNU_Linux_FOSS: linux框 ...

  2. 发布AI操作系统、应用市场,开源机器学习数据库和AI操作系统内核,第四范式这波操作有点秀!

    "AI的发展经历了'高期望--能否落地--落地是否有用"等多次潮起潮落.今天,AI的价值再次引发一些讨论和怀疑." 第四范式创始人兼首席执行官戴文渊在近日举行的新品发布会 ...

  3. 基于 Bochs 的操作系统内核实现

    简介 Bochs 简介 Bochs(读音Box)是一个开源的模拟器(Emulator),它可以完全模拟x86/x64的硬件以及一些外围设备.与VirtualBox / VMware等虚拟机(Virtu ...

  4. 公开课-C++学习路线实战导引:从0开始到操作系统内核开发

    公开课观看办法: 加入到51CTO学院C++交流群 431187655 在群中直播 课程简介 从整个IT行业角度出发, C/C++技术定位于后端服务与系统级软件研发工作,这意味着C/C++的从业人员应 ...

  5. Linux查看版本当前操作系统内核信息

    1. # uname -a (Linux查看版本当前操作系统内核信息) 输出 Linux xxx 4.4.0-31-generic #50~14.04.1-Ubuntu SMP Wed Jul 13 ...

  6. 深入理解操作系统内核架构(送书)!

    近年来,我国自主研发操作系统被反复提及.近期,一个计算机领域内非常专业的词来到了几乎所有人的视线内,这就是--微内核.人们对操作系统内核的讨论越来越热烈,甚至有人说我不懂什么叫微内核,什么是宏内核,接 ...

  7. 五分钟了解操作系统内核

    操作系统和内核 关于操作系统是这样定义的: 操作系统(英语:Operating System,缩写:OS)是管理计算机硬件与软件资源的系统软件,同时也是计算机系统的内核与基石.操作系统需要处理如管理与 ...

  8. 【OS学习笔记】二十二 保护模式六:保户模式下操作系统内核如何加载用户程序并运行 对应的汇编代码之用户程序

    本汇编代码对应文章:保户模式下操作系统内核如何加载用户程序并运行中的实际用户程序代码. 对应的主引导扇区代码:主引导扇区代码 对应的内核代码:内核代码 ;代码清单13-3;文件名:c13.asm;文件 ...

  9. 【OS学习笔记】二十一 保护模式六:保户模式下操作系统内核如何加载用户程序并运行 对应的汇编代码之内核代码

    本汇编代码对应文章保户模式下操作系统内核如何加载用户程序并运行 中的实际内核代码 对应的主引导扇区代码:主引导扇区代码 对应的用户程序代码:用户程序代码 ;代码清单13-2;文件名:c13_core. ...

最新文章

  1. C++数组名做函数形参/指针
  2. kitbash贫民区三维场景模型 Kitbash3d – Favelas
  3. C++继承中的构造与析构
  4. 【软件工程】关于计算机的一些问答与思考
  5. [PHP语法]PHP基础语法与数据类型
  6. 初识python之 APP store排行榜 蜘蛛抓取(一)
  7. 烂泥:mysql数据库使用的基本命令
  8. 漫画:这份程序员自画像,是不是你的?
  9. Linux双网卡bonding举例
  10. Listary Pro - 搜索、管理都挺好
  11. kindeditor上传图片php,KindEditor在php环境下上传图片功能集成的方法示例
  12. opencv读取视频转换成一张张图片
  13. opencv:图像的读取和显示
  14. 最小生成树-Borůvka算法
  15. 2011计算机一级a,计算机一级A2011 上海.doc
  16. android7.0后台,安卓7.0带来一键清理后台 真能使手机变快吗
  17. Win10登录界面隐藏其他账户
  18. Google VR开发-Cardboard VR SDK反畸变实现
  19. 2-44钟静雯_day04
  20. GNU Linux shell中如何进行各进制编码间(二进制、8进制、16进制、base64)的转换

热门文章

  1. qcc304x笔记之嵌入EQ模块(十二)
  2. 蓝牙芯片nRF51822开发系列(一):环境搭建和GPIO使用(点亮LED)
  3. ECSHOP+wamp
  4. 计算机CPU后面09B啥意思,电脑启动出现CPU FAN ERROR 解决方法【方法详解】
  5. index函数的使用方法
  6. 001.组织机构代码生成
  7. 商城API开发之下单接口
  8. oracle 全面预算,财辅全面预算管理系统的设计与实现(Eclipse,Oracle)
  9. siki学院案例---贪吃蛇 学习总结
  10. 74ls160/74ls161中文资料介绍