這兩天學寫操做系統進展不順,被卡住了!等搞清楚再繼續,就把調試的時候寫的幾個函數貼上來湊數吧。——win7下貌似沒有debug,有也不愛用,業餘屌絲仍是比較中意在代碼執行的時候直接輸出中間值來查錯。函數
第一個函數是顯示字符串的:oop
; 功能:顯示緊跟在調用指令後定義的字符串 ; 參數:無 ; 反值:無 ; 注意:本函數改變了寄存器 ax、si 的值,若有必要,父函數應在調用前自行保存 PrintMsg: pop si ; si = IP mov ah, 0x0E ; 功能號,0x0E:顯示一個字符,光標跟隨字符移動 .Loop: lodsb cmp al, 0 ; 字符串以 0 結尾 je .Return int 0x10 jmp .Loop .Return: push si ; 恢復 ip ret
這個很好用,不用預先定義字符串,要用的時候直接在 call 下一行定義字符串就行:spa
call PrintMessage db "Message 1 !", `\r\n`, 0
第二個是顯示數字的——把數字當字符串顯示, 有了這個不用在 debug 裏找變量中間值了!操作系統
; ---------------------------------------------------------------------------------------- ; 函數功能:以十六進制顯示 32 位整數字符形式 ; 入口參數:eax = 數據 ; 出口參數:無 PrintHex: push bp mov bp, sp push edx push ecx push eax push dword 0 push dword ' ' ; 求餘,把對應的數字轉換成 ASCII 碼,再壓入棧 mov ecx, 16 .Rem: xor edx, edx div ecx cmp edx, 9 jg .Hex add edx, '0' ; 餘數 0 - 9 轉成 ASCII 碼 jmp .Push .Hex: add edx, 'A' - 10 ; 餘數 10 - 15 轉成 ASCII 碼 .Push: push edx cmp eax, 0 jnz .Rem push dword 'x' ; 16 進制數以 0x 前綴表示 push dword '0' mov ah, 0x0E .Print: pop ecx jcxz .Return mov al, cl int 0x10 jmp .Print .Return: pop eax pop ecx pop edx mov sp, bp pop bp ret
第三個是正常顯示字符串的:debug
; ---------------------------------------------------------------------------------------- ; 函數功能:顯示字符串 ; 入口參數:ds : si = 字符串地址 ; 出口參數:無 PrintStr: push bp mov bp, sp push ax push si mov ah, 0x0E ; 功能號,0x0E:顯示一個字符,光標跟隨字符移動 .Print: lodsb cmp al, 0 ; 字符串以 0 結尾 je .Return int 0x10 jmp .Print .Return: pop si pop ax mov sp, bp pop bp ret
; ---------------------------------------------------------------------------------------- ; 函數功能:直接寫顯存顯示字符串 ; 入口參數:cl = 顏色屬性 ; dh、dl = 屏幕行(0 ~ 24)、列座標(0 ~ 79) ; ds : si = 待顯示字符串地址 ; 出口參數:無 ; 80 * 25 彩色字模式的顯存第一頁(共 4 頁)在內存中的地址爲 B8000H ~ B8F9FH,向該地址寫入 ; 內容將當即顯示在屏幕上,共可顯示 25 行、80 列,屏幕左上角爲原點(0,0)。 ; 每一個字符在顯存中佔兩個字節,第一個字節是 ASCII 碼,第二字節是顏色屬性(共 256 種): ; 位: 7 6 5 4 3 2 1 0 ; 含義: BL R G B I R G B ; 閃爍 背景顏色 高亮 前景顏色 ShowStr: push bp mov bp, sp push es push di push si push dx push cx push ax mov ax, 0x0B800 mov es, ax ; 由行列座標計算顯存偏移量 mov al, 160 mul dh mov di, ax mov al, 2 mul dl add di, ax .Loop: mov al, [ds : si] cmp al, 0 jz .Return mov [es : di], al mov [es : di + 1], cl inc si add di, 2 jmp .Loop .Return: pop ax pop cx pop dx pop si pop di pop es mov sp, bp pop bp ret