熱點推薦:
您现在的位置: 電腦知識網 >> 編程 >> Oracle >> 正文

自己動手寫操作系統(二)

2013-11-13 15:34:16  來源: Oracle 

  
  上一期我講述了如何在軟盤的啟動扇區寫一些代碼然後再從軟盤啟動的過程制作好一個啟動扇區在切換到保護模式之前我們還應該知道如何使用BIOS中斷BIOS中斷是一些由BIOS提供的為了使操作系統的創建更容易的低級程序在本文中我們將學習處理BIOS的中斷
  
  為什麼要用BIOS
  
  BIOS會把啟動扇區拷貝至RAM中並且執行這些代碼除此之外BIOS還要做很多其它的事情當一個操作系統剛開始啟動時系統中並沒有顯卡驅動軟盤驅動等任何驅動程序因此啟動扇區中不可能包含任何一個驅動程序我們要采取其它的途徑這個時候BIOS就可以幫助我們了BIOS中包含有各種可以使用的程序包括檢測安裝的設備控制打印機計算內存大小等用於各種目的的程序這些程序就是所說的BIOS中斷
  
  如何調用BIOS中斷
  
  在一般的程序設計語言中函數的調用是一件非常容易的事情比如在C語言中如果有一個名為display的程序它帶有兩個參數其中參數noofchar表示顯示的字符數參數attr表示顯示字符的屬性那麼要調用它只需給出程序的名稱即可對於中斷的調用我們使用的是匯編語言中的int指令
  
  比如在C語言中要顯示一些東西時使用的指令如下所示
  
  display(nofcharattr)
  
  而使用BIOS時要實現相同功能使用的指令如下
  
  int x
  
  如何傳遞參數
  
  在調用BIOS中斷之前我們需要先往寄存器中送一些特定的值假設要使用BIOS的中斷h該中斷的功能是把數據從軟盤傳送至內存之中在調用該中斷之前要先指定拷貝數據的段地址指定驅動器號磁道號扇區號以及要傳送的扇區數等等然後就要往相應的寄存器送入相應的值在進行下面的步驟前讀者有必要對這一點有比較明確地認識
  
  此外一個比較重要的事實是同一個中斷往往可以實現各種不同的功能中斷所實現的確切功能取決於所選擇的功能號功能號一般都存在ah寄存器之中比如中斷h可以用於讀磁盤寫磁盤等功能如果把送入ah寄存器中那麼中斷選擇的功能就是寫磁盤如果把送入ah寄存器中選擇的功能則是讀磁盤等
  
  我們要做的事情
  
  這次我們的源代碼由兩個匯編語言程序和一個C程序組成第一個匯編文件是引導扇區的代碼在引導扇區中我們寫的代碼是要把軟盤中第二扇區拷貝至內存段的x處(地址是x即偏移地址為)這時我們需要使用BIOS的中斷h這時啟動扇區的代碼就會把控制權轉移至x在第二個匯編文件中代碼會使用BIOS中斷h在屏幕上顯示一個信息C程序實現的功能則是把可執行的文件拷貝至啟動扇區把可執行的文件拷貝至軟盤的第二扇區
  
  啟動扇區代碼
  
  使用中斷h啟動扇區把軟盤第二扇區裡的內容加載至內存的x處(段地址為x)下面的代碼是用於實現這一目的的代碼將其保存至文件sbects中
  
  LOC=x
  entry start
  start:
   mov ax#LOC
   mov esax
   mov bx#
   mov dl#
   mov dh#
   mov ch#
   mov cl#
   mov al#
   mov ah#
   int x
   jmpi #LOC
  
  上面代碼第一行類似於一個宏接下去的兩行則是把值x加載至es寄存器中這是軟盤上第二扇區代碼將拷貝到的地方(第一扇區是啟動扇區)這時把段內的偏移設為
  
  接下來把驅動器號送入dl寄存器中其中磁頭號送入dl寄存器中磁道號送入ch寄存器中扇區號送入cl寄存器中扇區數送入al寄存器之中我們想要實現的功能是把扇區磁道號為驅動器號為的內容送至段地址x所有這些參數都和MB的軟盤相對應
  
  把送入ah寄存器中是選擇了由中斷h提供的相應功能即實現從軟驅轉移數據的功能
  
  最後調用中斷h並且轉至偏移為的段地址x
  
  第二個扇區的代碼
  
  第二個扇區中的代碼如下所示(把這些代碼保存至文件sbects之中)
  
  entry start
  start:
   mov ah#x
   xor bhbh
   int x
  
   mov cx#
   mov bx#x
   mov bp#mymsg
   mov ax#x
   int x
  
  loop: jmp loop
  mymsg:
   byte
   ascii Operating System is Loading
  
  上面代碼將被加載至段地址為x並且被執行在這段代碼中使用了中斷h來獲取目前的光標位置然後顯示信息
  
  從第行到第行用於得到目前光標的位置在此中斷h選用的是功能然後清除了bh寄存器的內容並把字符串送至ch寄存器中在bx中我們送入了頁碼及顯示的屬性此處我們想要在黑背景上顯示白色的字符然後把要顯示字符的地址送到bp之中信息由兩個字節組成其值分別為它們分別對應回車和LF(換行)的ASCⅡ值接下來是一個由個字符組成的串在下面實現的功能是輸出字符串然後移動光標最後是調用中斷然後進入循環
  
  C程序代碼
  
  C程序的源代碼如下所示將其存儲為writec文件
  
  #include /* unistdh needs this */
  #include /* contains read/write */
  #include
  int main()
  {
   char boot_buf[];
   int floppy_desc file_desc;
   file_desc = open(/bsect O_RDONLY);
   read(file_desc boot_buf );
   close(file_desc);
   boot_buf[] = x;
   boot_buf[] = xaa;
   floppy_desc = open(/dev/fd O_RDWR);
   lseek(floppy_desc SEEK_SET);
   write(floppy_desc boot_buf );
   file_desc = open(/sect O_RDONLY);
   read(file_desc boot_buf );
   close(file_desc);
   lseek(floppy_desc SEEK_SET);
   write(floppy_desc boot_buf );
   close(floppy_desc);
  }
  
  在上一期中我曾經介紹過如何操作能啟動的軟盤現在這一個過程稍微有點不同首先把由bsects編譯出來的可執行文件bsect拷貝至軟盤的啟動扇區然後再把由sects產生的可執行文件sect拷貝至軟盤的第二個扇區
  
  把上述文件置於同一目錄之下然後分別對其進行編譯方法如下所示
  
  as bsects o bsecto
  ld d bsecto o bsect
  
  對sects文件重復以上的操作得出可執行文件sect編譯writec插入軟盤後執行write文件命令如下所示
  
  cc writec o write
  /write
  
  下一步我們要做的事情
  
  從軟盤啟動以後可以看到顯示出來的字符串這是使用了BIOS中斷來完成的下一期要做的事情是在這個操作系統中實現實模式向保護模式的轉換

From:http://tw.wingwit.com/Article/program/Oracle/201311/16947.html
    Copyright © 2005-2013 電腦知識網 Computer Knowledge   All rights reserved.