段寄存器的兩種初始化方式

  實模式(real mode)下采用段地址:偏移地址的方式進行定位。在Masm中,有2種方式對段地址進行初始化,一就是編譯階段,再就是程序執行階段。

  一、彙編階段(Masm編譯階段):

  彙編階段通過Assume僞指令對段段寄存器的值進行指定(但並不對段寄存器真的賦值),而是按Assume指定的情況進行編譯。比如,在對標號進行編譯的時候,就根據Assume CS的值進行計算,如Assume中指定的段沒有相應的標號,則會提示錯誤;還有就是有多個代碼段的時候,要在適當的時候切換。其他在彙編階段需要段寄存器的情況我暫時還想不出,請指定的朋友告知一下,非常感謝!

  Assume 語法:

  Assume segementregister:name[,segementregister:name]

  Assume segementregister:nothing(取消指定)

  Assume nothing(取消所有指定)

  1、name的值可以是段名稱、組名稱、seg表達式或計算後爲段名稱或組名稱的字符串。

  2、assume可以在任何地方指定,如果重新指定(再次assume),之後的代碼的段寄存器已重新指定爲準。

  二、程序執行階段(Dos載入exe後,執行exe階段):

  程序執行階段段寄存器的值得初始化真實賦值給段寄存器的,而不是assume那樣假定。

  1、CS和IP寄存器:

   CS和IP寄存器的值都是在exe文件的psp段中進行初始化,即系統載入exe文件時初始化。psp中,CS的值是通過End [StartAddress]僞指令確定的。StartAddress可以是標號或表達式。IP得值基本都是0,可通過ORG指令修改,如com文件的ORG 100h。如果exe文件由多個obj文件組成,只能有一個文件指定CS的值,就像C語言只有一個main函數一樣,程序只能有一個起始地址。
  2、SS和SP寄存器:

  SS和SP寄存器也是在PSP中初始化(同上)。PSP中,SS和SP是通過類型爲STACK的段定義計算並賦值,SS對應段地址,SP指向段的尾部。

  3、DS寄存器:

  DS寄存器並不通過PSP初始化,必須通過代碼,所以大部分彙編程序前幾行的代碼都是對DS進行初始化,如:

mov ax,_DATA
mov ds,ax

  8086後續的ES、GS則同樣需要通過代碼進行初始化。

  ☆對於exe文件中的段地址,都只是相對地址。系統在加載exe文件時,都會在相對地址的基礎上,對相對地址進行重定位,即替換成物理地址,其他相對於段地址的偏移地址則無需處理。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章