nucleus OS操作系统详细介绍.
http://www.oschina.net/p/nucleus-os
我找了很久,才找到关于nasm汇编写的内核源码,不仅代码少,而且是值得学习的.麻雀虽小,但五脏俱全.
我这人比较菜,这个是我周边的人都这样认同的,不过确实我也比较菜,所以和大家学习和进步吧.
我们从最简单的版本开始分析源码:
nucboot 目录: 引导程序
nucload 目录: 跳转保护模式
nucleus 目录: 系统的第一个任务,驱动,头文件,中等等一些...
nucinst 目录: 写入系统等等一些的C程序
=====================================================
我先开始分析引导程序代码:
看nucboot目录下的makefile文件: nasm -f bin boot_fd.asm -o boot_fd.bin ,这是编译nasm代码成二进制文件bin.
代码就那么多,要学习的话,需要汇编,C语言,IA-32,实模式到保护模式,操作系统原理,微机原理的知识就完了,不需要你学的很深,
就像我这样的人,很菜的那种,智商平平,什么都不懂的,都看懂了,你怕什么呢?
引导程序必要从0x7c00开始(对于大多数机器),大小必须为512B,最后两个字节必须标识: 0xaa55h.
为何要这样,都是搞硬件的人规定的,反正我是没有那个能力自己造硬件,自己规定自己的一套,所以就老老实实的先用别人的,有能力了才去谈论这些没有边界的事情。
; Nucleus BOOTLOADER 0.01
; (C)Copyright 2003 by Christian Lins
; This program is free software; you can redistribute it and/or modify it under the terms of the GNU
; General Public License as published by the Free Software Foundation; either version 2 of the License, ; or (at your option) any later version.
; This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without
; even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General ; Public License for more details.
; You should have received a copy of the GNU General Public License along with this program; if not,
; write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
; Letzte 膎derung: 24.05.2003
; Enth鋖t den Bootsektor, der den Kernelstarter (nucload) aufruft.
start:
org 0x7c00 ; Legt die Position im Segment fest. BIOS l鋎 von 0x7c00 org指定开始地址为0x7c00
;程序一开始就输出了四条废话.你可以将displaystring想象成C语言的printf吧,这样大家都比较好理解点.
mov si, msg_osname
call displaystring
mov si, msg_copyright
call displaystring
mov si, msg_ver
call displaystring
mov si, msg_nucload
call displaystring
; Bootlaufwerk bestimmen
cli ; Interrupts abschalten
mov ax, 0x9000 ; Adresse des Stack bestimmen
mov ss, ax ; ss=9000, Stackadresse festlegen
xor sp, sp ; Stackpointer auf Null setzen
sti ; Interrupts wieder an
mov [bootdrive], dl ; Laufwerk (Info in DL) in bootdrive speichern
mov si, msg_dot
call displaystring
; nucload von Floppy lesen und in Speicher kopieren
; WICHTIG: Kernel hier auch in den Speicher lesen!!!!!
; Im Moment l鋟ft nucleus nur mit dem ChaOS Bootsektor!
floppy_reset:
push ds
xor ax, ax ; ax=0
mov dl, [bootdrive]
int 13h ; Interrupt 13h wird aufgerufen
pop ds
jc short floppy_reset ; Jump if Carry-Flag gesetzt
;push es
floppy_load:
mov ax, 0x0050 ; es:ax= Segment 0050h
mov es, ax
xor bx, bx ; bx=0
mov ah, 2 ; Funktion Sektor laden
mov al, 5 ; Anzahl der Sektoren
mov cx, 2 ; Spur 0, Sektor 2 (ch/cl)
xor dx, dx ; dx=0, Seite=0 Laufwerk=0
int 13h
jc short floppy_load
mov si, msg_dot
call displaystring
; Sprung zu nucload
mov si, msg_dot
call displaystring
mov ax, 0x0050 ; nucload ist im Segment 1000h
mov es, ax
mov ds, ax
push ax
xor ax, ax ; ax=0
push ax
retf
; Funktionen
displaystring:
lodsb
or al,al
jz short finish
mov ah,0x0E ; Zeigt ein Char an
mov bx,0x0007
int 0x10
jmp displaystring
finish:
retn
; Strings
msg_osname db 13, 10, 13, 10, 13, 10, 'ChaOS Version 0.01', 13, 10, 0
msg_copyright db '(C)2003 by Jens Muehlenhoff', 13, 10, 13, 10, 0
msg_nucload db 'Lade //boot/nucload', 0
msg_dot db '.', 0
msg_ver db 'Bootloader Version 0.01 (02.06.2003)', 13, 10, 0
bootdrive db 0
times 512-($-$$)-2 db 0 ;这段是将510剩下的字节填充为0,但是这段代码写繁琐了,可以改成: 510-($-$$) db 0 ,但是作者这样写就比较好理解.
dw 0AA55h
msg_osname 中的13,10代表不是数字.assic码值,查看就知道,13是'\r' [\r: 回车,光标到本行行首],10是'\n' [\n: 换行, 光标到下行行首],所以13,10他们是连在一起的,你可以想象变成了我们键盘上的回车键.
要是你强烈认为是数字,你可以查看代码 displaystring 中的 lodsb. lodsb是串操作指令.
mov si, msg_osname
call displaystring
这段代码和displaystring之间发生了什么呢?
si 保存了 msg_osname的地址. si 主要作用于 lodsb. si会根据标志位的DF来确定方向,SI是应该加还是减.
DF=0,从低地址向高地址,即每次操作后SI、DI递增
DF=1,从高地址向低地址,即每次操作后SI、DI递减
在displaystring函数中: 使用了BIOS中断调用:
功能号:0EH
功能:在Teletype模式下显示字符
入口参数:AH=0EH
AL=字符
BH=页码
BL=前景色(图形模式)
出口参数: 无