這是讀書筆記
Learn More →
作者:鄭鋼
出版社:佳魁資訊股份有限公司
出版日期:2017/05/31
這邊討論都是 x86 架構下的組合語言,組譯工具是 nasm
,
如果是 ARM 架構下的組合語言,組譯工具是 armasm
。
Learn More →
參考資料:CPU Registers x86
CPU 分成三個部分:控制單元、運算單元、儲存單元。
CPU 定址模式:
真實模式下的 ret/retf。
真實模式下的 call。
真實模式下的 jmp。
標示暫存器 flags。
Learn More →
Conditional Jumps
Learn More →
ARM 通常使用 MMI/O。
Learn More →
;主引導程序
;
;LOADER_BASE_ADDR equ 0xA000
;LOADER_START_SECTOR equ 0x2
;------------------------------------------------------------
SECTION MBR vstart=0x7c00
mov ax,cs
mov ds,ax
mov es,ax
mov ss,ax
mov fs,ax
mov sp,0x7c00
mov ax,0xb800
mov gs,ax
; 清屏
;利用0x06號功能,上卷全部行,則可清屏。
; -----------------------------------------------------------
;INT 0x10 功能號:0x06 功能描述:上卷窗口
;------------------------------------------------------
;輸入:
;AH 功能號= 0x06
;AL = 上卷的行數(如果為0,表示全部)
;BH = 上卷行屬性
;(CL,CH) = 窗口左上角的(X,Y)位置
;(DL,DH) = 窗口右下角的(X,Y)位置
;無返回值:
mov ax, 0600h
mov bx, 0700h
mov cx, 0 ; 左上角: (0, 0)
mov dx, 184fh ; 右下角: (80,25),
; 因為VGA文本模式中,一行只能容納80個字符,共25行。
; 下標從0開始,所以0x18=24,0x4f=79
int 10h ; int 10h
; 輸出背景色綠色,前景色紅色,並且跳動的字符串"1 MBR"
mov byte [gs:0x00],'1'
mov byte [gs:0x01],0xA4 ; A表示綠色背景閃爍,4表示前景色為紅色
mov byte [gs:0x02],' '
mov byte [gs:0x03],0xA4
mov byte [gs:0x04],'M'
mov byte [gs:0x05],0xA4
mov byte [gs:0x06],'B'
mov byte [gs:0x07],0xA4
mov byte [gs:0x08],'R'
mov byte [gs:0x09],0xA4
jmp $ ; 通過死循環使程序懸停在此
times 510-($-$$) db 0
db 0x55,0xaa
nasm -o mbr.bin mbr.S
dd if=../code/mbr.bin of=./sr_hd60m.img bs=512 count=1 conv=notrunc
Learn More →
./bochs -debugger
查看 help 資訊
查看 BIOS 的入口點:0xFFFF0
反組譯機器碼
查看 MBR 的入口點:0x7c00
一開始是沒有值,BIOS 負責把 MBR 從硬碟載到 0x7c00
順便可以看看 BIOS 吐出來的資訊,而游標的位置就是上一章的範例,MBR 印出字元的位置。
一些歷史和原理介紹我就不贅述了。
0x1F7 / 0x177 Status Register for read.
boot.inc
;------------- loader和kernel ----------
LOADER_BASE_ADDR equ 0x900
LOADER_START_SECTOR equ 0x2
mbr.S
;主引導程序
;------------------------------------------------------------
%include "boot.inc"
SECTION MBR vstart=0x7c00
mov ax,cs
mov ds,ax
mov es,ax
mov ss,ax
mov fs,ax
mov sp,0x7c00
mov ax,0xb800
mov gs,ax
; 清屏
;利用0x06號功能,上卷全部行,則可清屏。
; -----------------------------------------------------------
;INT 0x10 功能號:0x06 功能描述:上卷窗口
;------------------------------------------------------
;輸入:
;AH 功能號= 0x06
;AL = 上卷的行數(如果為0,表示全部)
;BH = 上卷行屬性
;(CL,CH) = 窗口左上角的(X,Y)位置
;(DL,DH) = 窗口右下角的(X,Y)位置
;無返回值:
mov ax, 0600h
mov bx, 0700h
mov cx, 0 ; 左上角: (0, 0)
mov dx, 184fh ; 右下角: (80,25),
; 因為VGA文本模式中,一行只能容納80個字符,共25行。
; 下標從0開始,所以0x18=24,0x4f=79
int 10h ; int 10h
; 輸出字符串:MBR
mov byte [gs:0x00],'1'
mov byte [gs:0x01],0xA4
mov byte [gs:0x02],' '
mov byte [gs:0x03],0xA4
mov byte [gs:0x04],'M'
mov byte [gs:0x05],0xA4 ;A表示綠色背景閃爍,4表示前景色為紅色
mov byte [gs:0x06],'B'
mov byte [gs:0x07],0xA4
mov byte [gs:0x08],'R'
mov byte [gs:0x09],0xA4
mov eax,LOADER_START_SECTOR ; 起始扇區lba地址
mov bx,LOADER_BASE_ADDR ; 寫入的地址
mov cx,1 ; 待讀入的扇區數
call rd_disk_m_16 ; 以下讀取程序的起始部分(一個扇區)
jmp LOADER_BASE_ADDR
;-------------------------------------------------------------------------------
;功能:讀取硬盤n個扇區
rd_disk_m_16:
;-------------------------------------------------------------------------------
; eax=LBA扇區號
; ebx=將數據寫入的內存地址
; ecx=讀入的扇區數
mov esi,eax ;備份eax
mov di,cx ;備份cx
;讀寫硬盤:
;第1步:設置要讀取的扇區數
mov dx,0x1f2
mov al,cl
out dx,al ;讀取的扇區數
mov eax,esi ;恢覆ax
;第2步:將LBA地址存入0x1f3 ~ 0x1f6
;LBA地址7~0位寫入端口0x1f3
mov dx,0x1f3
out dx,al
;LBA地址15~8位寫入端口0x1f4
mov cl,8
shr eax,cl
mov dx,0x1f4
out dx,al
;LBA地址23~16位寫入端口0x1f5
shr eax,cl
mov dx,0x1f5
out dx,al
shr eax,cl
and al,0x0f ;lba第24~27位
or al,0xe0 ; 設置7~4位為1110,表示lba模式
mov dx,0x1f6
out dx,al
;第3步:向0x1f7端口寫入讀命令,0x20
mov dx,0x1f7
mov al,0x20
out dx,al
;第4步:檢測硬盤狀態
.not_ready:
;同一端口,寫時表示寫入命令字,讀時表示讀入硬盤狀態
nop
in al,dx
and al,0x88 ;第4位為1表示硬盤控制器已準備好數據傳輸,第7位為1表示硬盤忙
cmp al,0x08
jnz .not_ready ;若未準備好,繼續等。
;第5步:從0x1f0端口讀數據
mov ax, di
mov dx, 256
mul dx
mov cx, ax ; di為要讀取的扇區數,一個扇區有512字節,每次讀入一個字,
; 共需di*512/2次,所以di*256
mov dx, 0x1f0
.go_on_read:
in ax,dx
mov [bx],ax
add bx,2
loop .go_on_read
ret
times 510-($-$$) db 0
db 0x55,0xaa
nasm -I inc/ -o mbr.bin mbr.S
dd if=../code/mbr.bin of=./sr_hd60m.img bs=512 count=1 conv=notrunc
loader.S
%include "boot.inc"
section loader vstart=LOADER_BASE_ADDR
; 輸出背景色綠色,前景色紅色,並且跳動的字符串"1 MBR"
mov byte [gs:0x20],'2'
mov byte [gs:0x21],0xA4 ; A表示綠色背景閃爍,4表示前景色為紅色
mov byte [gs:0x22],' '
mov byte [gs:0x23],0xA4
mov byte [gs:0x24],'L'
mov byte [gs:0x25],0xA4
mov byte [gs:0x26],'O'
mov byte [gs:0x27],0xA4
mov byte [gs:0x28],'A'
mov byte [gs:0x29],0xA4
mov byte [gs:0x2a],'D'
mov byte [gs:0x2b],0xA4
mov byte [gs:0x2c],'E'
mov byte [gs:0x2d],0xA4
mov byte [gs:0x2e],'R'
mov byte [gs:0x2f],0xA4
jmp $ ; 通過死循環使程序懸停在此
nasm -I inc/ -o loader.bin loader.S
dd if=../code/loader.bin of=./sr_hd60m.img bs=512 count=1 seek=2 conv=notrunc
or
By clicking below, you agree to our terms of service.
New to HackMD? Sign up