30天自制操做系統(二)彙編語言學習與Makefile入門

 

1 介紹文本編輯器

 

這部分可直接略過html

 

2 繼續開發

 

helloos.nas中核心程序以前的內容和啓動區之外的內容先不講了,由於還涉及到一些軟盤方面的知識。小程序

而後來說的是helloos.nas這個文件編輯器

 

; hello-os
; TAB=4

        ORG        0x7c00             ; 指明程序的裝載地址

; 如下這部分記錄的是FAT12格式的軟盤

        JMP        entry
        DB         0x90
        DB         "HELLOIPL"         ; 啓動扇區的名稱能夠是任意的字符串 (8字節)
        DW         512                ; 每一個扇區(sector)的大小(必須是512字節)
        DB         1                  ; 簇(cluster)的大小 (必須爲512字節)
        DW         1                  ; FAT的起始位置 (通常從第一個扇區開始)
        DB         2                  ; FAT的個數 (必須爲2)
        DW         224                ; 根目錄的大小(通常設成224項)
        DW         2880               ; 該磁盤的大小(必須是2880扇區)
        DB         0xf0               ; 磁盤的種類 (必須是0xf0)
        DW         9                  ; FAT的長度 (必須是9扇區)
        DW         18                 ; 1個磁道(track)有幾個扇區(必須是18)
        DW         2                  ; 磁頭數 (必須是2)
        DD         0                  ; 不使用分區, 必須是0
        DD         2880               ; 重寫一次磁盤大小
        DB         0,0,0x29           ; 意義不明, 固定
        DD         0xffffffff         ; (多是)卷標號碼
        DB         "HELLO-OS   "      ; 磁盤的名稱(11字節)
        DB         "FAT12   "         ; 磁盤格式名稱 (8字節)
        RESB       18                 ; 先空出18字節

; 程序主體

entry:
        MOV        AX,0               ; 初始化寄存器
        MOV        SS,AX
        MOV        SP,0x7c00
        MOV        DS,AX
        MOV        ES,AX
        MOV        SI,msg
putloop:
        MOV        AL,[SI]
        ADD        SI,1               ; 給SI加1
        CMP        AL,0
        JE         fin
        MOV        AH,0x0e            ; 顯示一個文字
        MOV        BX,15              ; 指定字符顏色
        INT        0x10               ; 調用顯卡BIOS
        JMP        putloop
fin:
        HLT                           ; 讓CPU中止等待指令
        JMP        fin                ; 無限循環

msg:
        DB         0x0a, 0x0a         ; 換行2次
        DB         "hello, world"
        DB         0x0a               ; 換行
        DB         0
        RESB       0x7dfe-$           ; 填寫0x00, 直到0x7dfe
        DB         0x55, 0xaa

; 如下是啓動區之外部分的輸出
        DB         0xf0, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00
        RESB       4600
        DB         0xf0, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00
        RESB       1469432

 

ORG指令

 

ORG指令告訴nask,在開始執行的時候,把這些機器語言指令裝載到內存中的哪一個地址。函數

這條指令使得$的含義也發生了變化,再也不是指輸出文件的第幾個字節,而是表明將要讀入的內存地址。oop

 

ORG是"origin","源頭、起點"的意思,它會告訴nask,程序要從指定的這個地址開始也就是要把程序裝載到內存中的指定地址。spa

 

JMP,JE指令

至關於C語言中的goto標籤,多年以來咱們都被教育不要用goto......操作系統

"JMP entry"這個指令就是讓CPU執行內存地址爲entry處的程序。3d

標籤code

在上面的程序中entry,fin,putloop和msg都是標籤,至關於一個入口地址,或者標記。htm

每一個標號對應的數字,都是由彙編語言編譯器根據ORG指令計算出來的。編譯器計算出的"標號的地方對應的內存地址"就是那個標號的值。

 

MOV指令

 

CPU中的各類寄存器

 

彙編中[]取值

 

MOV AL, SI的意思是將SI寄存器中的值傳給AL寄存器,可是MOV AL, [SI]的意思將SI中存儲着一個數字,而這個數字表明的是內存中的一個地址,[SI]意思是取出這個地址應對的值。

 

MOV BYTE [678], 123

MOV WORD [678], 123

 

數據大小端的問題

 

INT指令

 

INT是軟件中斷指令。意思是打斷CPU當前的執行路徑,跑去其餘的地方執行。

BIOS中存儲了爲開發人員準備的各類函數的集合,INT指令後面接不通的數字,就調用BIOS中對應的函數了。

 

HLT指令

HLT讓CPU中止動做的指令,不過並非完全的中止,而是讓CPU進行待機狀態,只要外部發生變化,好比按下鼠標鍵盤,就會醒過來,繼續執行程序。

若是沒有HLT指令,CPU會不停的只去執行JMP指令,負荷達到100%,很是費電。

 

0x7c00

 

如今的內存地址都很大了,尼瑪,內存今年漲價好厲害。

內存的0號地址,也就是最開始的地方,是BIOS程序用來實現各類不一樣功能的地方,若是隨便使用就會與BIOS發生衝突。

此外,在內存的0xf0000號地址附近還存放着BIOS程序自己,也不能使用。

內存還有很多地方也是不能使用的,做爲操做系統開發者要特別注意。

 

0x00007c00~0x00007dff:啓動區內容的裝載地址

 

程序中ORG指令指的就是這個地址。

 

文中沒有解釋爲啥是0x7C00,我又在網上找了一下

 

一下內容來自阮一峯老師博客

=================== start_1 =======================

《計算機原理》課本說,啓動時,主引導記錄會存入內存地址0x7C00。
這個奇怪的地址,是怎麼來的,課本就不解釋了。我一直有疑問,爲何不存入內存的頭部、尾部、或者其餘位置,而恰恰存入這個比 32KB 小1024字節的地方?
昨天,我讀到一篇文章,終於解開了這個謎。

image

首先,若是你不知道,主引導記錄(Master boot record,縮寫爲MBR)是什麼,能夠先讀《計算機是如何啓動的?》。
簡單說,計算機啓動是這樣一個過程。

  1. 通電
  2. 讀取ROM裏面的BIOS,用來檢查硬件
  3. 硬件檢查經過
  4. BIOS根據指定的順序,檢查引導設備的第一個扇區(即主引導記錄),加載在內存地址 0x7C00
  5. 主引導記錄把操做權交給操做系統

因此,主引導記錄就是引導"操做系統"進入內存的一段小程序,大小不超過1個扇區(512字節)。
image

0x7C00這個地址來自Intel的第一代我的電腦芯片8088,之後的CPU爲了保持兼容,一直使用這個地址。

image

1981年8月,IBM公司最先的我的電腦IBM PC 5150上市,就用了這個芯片。

image

當時,搭配的操做系統是86-DOS。這個操做系統須要的內存最少是32KB。咱們知道,內存地址從0x0000開始編號,32KB的內存就是0x0000~0x7FFF。
8088芯片自己須要佔用0x0000~0x03FF,用來保存各類中斷處理程序的儲存位置。(主引導記錄自己就是中斷信號INT 19h的處理程序。)因此,內存只剩下0x0400~0x7FFF可使用。
爲了把儘可能多的連續內存留給操做系統,主引導記錄就被放到了內存地址的尾部。因爲一個扇區是512字節,主引導記錄自己也會產生數據,須要另外留出512字節保存。因此,它的預留位置就變成了:

0x7FFF - 512 - 512 + 1 = 0x7C00

0x7C00就是這樣來的。
計算機啓動後,32KB內存的使用狀況以下。

image

=================== end_1 =======================

就欣賞阮老師挖到底的情懷

 

因此其實啓動區就放到了0x7c00的位置,比32KB少1KB,記住這個,到時候裝個B。

 

image

 

3 先製做啓動區

 

這裏做者說並不想用nask來製做整個磁盤映像,而是先只用它來製做啓動區,去掉了後半段,程序也更名爲ipl.nas。

 

image

大概就是這一段內容去掉了,就是隻留到了55 AA了,還記得55AA了,第一個扇區最後的兩個字節哦。

 

4 Makefile入門

 

這裏就不講了,就是把來須要手動輸入的編譯命令用寫成Makefile這個文件。

 

數據也能執行麼?

CPU執行的是啥,指令,指令就是數據,CPU先找指令,再找操做數。你隨便給一段數據CPU,CPU也能執行。

這裏的意思就是,瞎幾把給CPU傳指令和數據,CPU執行的結果坑定也是亂七八糟的。

相關文章
相關標籤/搜索