//計算機啟動時cs=0xf000,ip=0xfff0,屬於bios的位址範圍,執行bios rom中的**
//bios程式檢查硬體(post),設定實模式下的中斷向量表,指向bios晶元自身提供的bios中斷呼叫的**
//最後,bios把bootsect載入到記憶體中的0000:7c00處
//此時cs=0x0000,ip=0x7c00,ss、sp不變,仍然使用和bios程式使用的堆疊段
//引導扇區bootsect的作用:移動bootsect自身到0x90000,載入setup模組到0x90200,載入system模組到0x10000
syssize=0x3000 //預設核心的最大長度
.globl begtext, begdata, begbss, endtext, enddata, endbss
.text
begtext:
.data
begdata:
.begbss
begbss:
.text
setuplen = 4 //setup程式所佔的扇區數
bootseg = 0x7c00
//bootsect的初始段位址,其實此時cs=0x0000,ip=0x7c00,但bootsect程式認為cs=0x7c00,ip=0;表示的位址是一樣的
//在移到initseg之前只要不使用label表示的偏移位址就不會出錯,因為編譯器認為編譯位址的起始偏移量為0
initseg = 0x9000 //移動bootsect的新段位址
setupseg = 0x9020
sysseg = 0x1000
endseg = sysseg + syssize
root_dev = 0x306 //指定root檔案系統是第2個硬碟的第乙個分割槽
entry start
start:
//移動bootsect自身到0x9000
mov ax, #bootseg
mov ds, ax
mov ax, #initseg
mov es, ax
mov cx, #256
sub si, si
sud di, di
repmovw
//移動bootsect自身到0x9000
jmpi go, initseg
go: mov ax, cs
mov ds, ax
mov es, ax
mow ss, ax
mov sp, #0xff00
load_setup:
mov dx, #0x0000 //驅動器0,磁頭0
mov cx, #0x0002 //扇區2,磁軌0
mov bx, #0x0200 //initseg端512偏移處
mov ax, #0x0200+setuplen //服務號2,扇區數4
int 0x13
jnc ok_load_setup
mov dx, #0x0000
mov ax, #0x0000 //復位磁碟
int 0x13
j load_setup
ok_load_setup:
mov dl,#0x00
mov ax,#0x0800 //服務號8,獲取磁碟引數
int 0x13
mov ch,#0x00
seg cs
mov sectors,cx //儲存每磁軌扇區數。
mov ax,#initseg
mov es,ax
//顯示資訊'loading system ...'
mov ah,#0x03
xor bh,bh
int 0x10
mov cx,#24 ! 共24 個字元。
mov bx,#0x0007 ! page 0, attribute 7 (normal)
mov bp,#msg1
mov ax,#0x1301 ! write string, move cursor
int 0x10
//現在開始將system 模組載入到0x10000(64k)處。
mov ax,#sysseg
mov es,ax
call read_it //讀磁碟上system模組
call kill_motor //關閉驅動器馬達
seg cs
mov ax,root_dev
cmp ax,#0
jne root_defined
seg cs
mov bx,sectors
mov ax,#0x0208
cmp bx,#15
je root_defined
mov ax,#0x021c
cmp bx,#18
je root_defined
undef_root:
jmp undef_root
root_defined:
seg cs
mov root_dev,ax
//所有程式都載入完畢,跳轉到setup程式去
jmpi 0,setupseg
sread: .word 1+setuplen
head: .word 0
track: .word 0
read_it:
mov ax,es
test ax,#0x0fff
die:
jne die
xor bx,bx
rp_read:
mov ax,es
cmp ax,#endseg
jb ok1_read
retok1_read:
seg cs
mov ax,sectors
sub ax,sread
mov cx,ax
shl cx,#9
add cx,bx
jnc ok2_read
je ok2_read
xor ax,ax
sub ax,bx
shr ax,#9
ok2_read:
call read_track
mov cx,ax
add ax,sread
seg cs
cmp ax,sectors
jne ok3_read
mov ax,#1
sub ax,head
jne ok4_read
inc track
ok4_read:
mov head,ax
xor ax,ax
ok3_read:
mov sread,ax
shl cx,#9
add bx,cx
jnc rp_read
mov ax,es
add ax,#0x1000
mov es,ax
xor bx,bx
jmp rp_read
read_track:
push ax
push bx
push cx
push dx
mov dx,track
mov cx,sread
inc cx
mov ch,dl
mov dx,head
mov dh,dl
mov dl,#0
and dx,#0x0100
mov ah,#2
int 0x13
jc bad_rt
pop dx
pop cx
pop bx
pop ax
retbad_rt:
mov ax,#0
mov dx,#0
int 0x13
pop dx
pop cx
pop bx
pop ax
jmp read_track
kill_motor:
push dx
mov dx,#0x3f2 ! 軟碟機控制卡的驅動埠,只寫
mov al,#0 ! a 驅動器,關閉fdc,禁止dma和中斷請求,關閉馬達
outb ! 將al 中的內容輸出到dx 指定的埠去
pop dx
retsectors:
.word 0 ! 存放當前啟動軟盤每磁軌的扇區數
msg1:
.byte 13,10 ! 回車、換行的ascii 碼
.ascii "loading system ..."
.byte 13,10,13,10 ! 共24 個ascii 碼字元
.org 508 ! 表示下面語句從位址508(0x1fc)開始,所以root_dev
! 在啟動扇區的第508 開始的2 個位元組中
root_dev:
.word root_dev ! 這裡存放根檔案系統所在的裝置號(init/main.c 中會用)
boot_flag:
.word 0xaa55 ! 硬碟有效標識
.text
endtext:
.data
enddata:
.bss
endbss:
硬碟主引導扇區引導程式
硬碟主引導扇區的引導程式只佔139個位元組 不同版本的fdisk 不同的分割槽程式寫入的主引導記錄會不相同,但其基本功能一樣 經過反彙編後的引導程式的彙編 如下 1000 0600 fa cli 自舉,將0000 7c00開始的硬碟主引導記錄本身轉移到0000 0600處,空出0000 7c00開始...
寫引導扇區所得
引導扇區的作用 首先引導扇區是位於磁碟的第乙個扇區內的,系統啟動時如果從此磁碟載入會直接讀這第乙個扇區,然後由第乙個扇區中的 載入 載入作業系統的loader 這樣再跳轉到loader內執行。引導扇區的主要思路 讀取假設為loader.bin的檔案,我寫的時候是按照fat12格式組織引導扇區的,自己...
05 主引導扇區
計算機加電或者復位後將讀取0磁軌 0磁頭 1扇區共512位元組到0x0000 0x7c00 處,然後判斷它是否有效。乙個有效的主引導扇區最後2位元組是0x55,0xaa。文字模式和圖形模式是顯示卡的2中基本工作模式。訪問視訊記憶體需要和顯示卡這個外圍裝置打交道,外圍裝置相對cpu都是慢速 低效率的。...