程序機(jī)器級表示

通過閱讀匯編代碼,我們能夠理解編譯器的優(yōu)化能力狸涌,并分析出代碼中潛在的低效率。

一最岗、機(jī)器級代碼

在整個編譯過程中帕胆,編譯器會完成大部分工作,將把C提供的相對比較抽象的執(zhí)行模型表示的程序轉(zhuǎn)化為處理器執(zhí)行的非嘲愣桑基本的指令懒豹。與目標(biāo)代碼相比,匯編代碼是可讀性更好的文本格式表示驯用。能夠理解匯編代碼以及它是如何與原始C代碼相對應(yīng)脸秽,是理解計算機(jī)如何執(zhí)行程序的關(guān)鍵一步。

對C程序員屏蔽的處理器狀態(tài)可見的

  • 程序計數(shù)器(%eip):表示將要執(zhí)行下一條指令在存儲器中的地址
  • 整數(shù)寄存器文件包含8個被命名的位置蝴乔,分別存儲32位的值记餐。這些寄存器可以存儲地址(對應(yīng)于C的指針)或整數(shù)數(shù)據(jù)。有的寄存器用來記錄某些重要的程序狀態(tài)薇正,其他寄存器用來保存臨時數(shù)據(jù)剥扣。
  • 條件寄存器保存最近執(zhí)行的算術(shù)指令狀態(tài),實現(xiàn)控制流中的條件變化铝穷,比如if或while
  • 浮點寄存器文件包含8個位置钠怯,用來存放浮點數(shù)據(jù)

(1)代碼示例

假設(shè)我們寫了一個C代碼文件code.c,包含下面這樣的過程定義

int accum = 0;

int sum(int x, int y)
{
    int t = x + y;
    acum += t;
    return t;
}

在命令行執(zhí)行”-S“選項,看到C編譯器產(chǎn)生的匯編代碼

unix> gcc -O2 -S code.c

編譯器產(chǎn)生一個匯編文件code.s曙聂,不做其他近一步工作
匯編代碼文件包含各種聲明

sum:
    pushl %ebp
    movl %esp,%ebp
    mov1 12(%ebp),%eax 
    addl 8(%ebp),%eax
    addl %eax,accum
    mov1 %ebp,%esp
    pop1 %ebp
    ret

上面代碼中每個縮進(jìn)去的行都對應(yīng)于一條機(jī)器指令晦炊。比如pushl 指令表示應(yīng)該將寄存器%ebp的內(nèi)容壓入棧中。

(2)訪問信息

一個IA32中央處理單元(cpu)包含一組8位值的寄存器,這些寄存器用來存儲整數(shù)數(shù)據(jù)和指針断国。下圖顯示了8個寄存器贤姆,以%e開頭。在過程處理中稳衬,對前三個寄存器(%eax,%ecx和%edx)的保存和恢復(fù)慣例將不同于接下來的三個寄存器(%ebx,%edi,%esi)霞捡,最后兩個寄存器(%ebp和%esp)保存著指向棧中重要位置的指針,只有根據(jù)棧慣例的標(biāo)準(zhǔn)才能修改這兩個寄存器中的值

(a)操作指示符

大多數(shù)指令都有一個或多個操作數(shù)薄疚,指示出執(zhí)行一個操作中藥引用的源數(shù)據(jù)值碧信,以及放置結(jié)果的目的位置。源數(shù)據(jù)值可以以常數(shù)形式給出街夭,或是從寄存器或存儲器中讀出砰碴,結(jié)果可以存放在寄存器或存儲器中。

各種操作數(shù)可能被分為三種類型板丽。

  • 立即數(shù)呈枉,也就是常數(shù)值。后面跟著一個整數(shù)埃碱,比如-577或$0x1F
  • 寄存器猖辫,某個寄存器中的內(nèi)容
  • 存儲器引用,根據(jù)計算出來的地址(有效地址)訪問某個存儲器位置砚殿。

有多種尋址模式:允許不同形式的存儲器引用住册。立即數(shù)偏移,基址寄存器瓮具,變之或索引寄存器荧飞,伸縮因子(必需是1、2名党、4叹阔、8)。

(3)數(shù)據(jù)傳送指令

最頻繁的指令是執(zhí)行數(shù)據(jù)傳送指令传睹。操作符指令能夠完成許多機(jī)器中要好幾條指令才能完成的功能耳幢。下圖列出一些重要的數(shù)據(jù)傳送指令,最常用的是傳送雙字的movl指令欧啤。

源操作數(shù)指令一個值睛藻,它可以是立即數(shù),可以存放在寄存器中邢隧,也可以存放在存儲器中店印。目的操作數(shù)指定一個位置,它可以是寄存器倒慧,也可以是存儲器地址按摘。

數(shù)據(jù)傳輸指令.jpg

第一個是原操作數(shù)包券,第二個是目的操作數(shù)。

movb指令是類似的炫贤,除了它只傳送一個字節(jié)溅固。movw傳送兩個字節(jié)。movsbl和movzbl指令負(fù)責(zé)拷貝一個字節(jié)兰珍,并設(shè)置目的操作數(shù)中其余的位侍郭。movsbl指令的源操作數(shù)時單字節(jié)的,它執(zhí)行符號擴(kuò)展到32位(將高24位設(shè)置為源字節(jié)的最高位)掠河,然后拷貝到雙字的目的中亮元。movzbl指令的源操作數(shù)時單字節(jié)的,在前面加24個0擴(kuò)展到32位口柳,并將結(jié)果拷貝到雙字的目的中。

pushl和popl指令都只有一個操作數(shù)----同于壓入的數(shù)據(jù)源和用于彈出的目的數(shù)據(jù)有滑。程序棧存放在儲存器中某個區(qū)域跃闹。%esp保存棧頂元素的地址

(4) 算術(shù)和邏輯操作

(a)加載有效地址

加載有效地址(leal)實際上是movl指令的變形,從存儲器讀數(shù)據(jù)到寄存器毛好,實際上根本沒有引用存儲器望艺。第一個操作看上去是一個寄存器引用,但該指令并不是從指定的位置讀入數(shù)據(jù)肌访,而是將有效地址寫入到目的操作數(shù)(如寄存器)找默。C中&S說明這種操作,為后面的存儲器引用產(chǎn)生指針吼驶。例子惩激,如果寄存器%eax值為x,指令leal 7(%edx,%eax ,4),%eax將設(shè)置寄存器%eax的值為x,那么leal 7(%edx,%edx,4),%eax將設(shè)置%eax的值為5x+7。注意目的操作數(shù)必須是寄存器蟹演。

(b)一元和二元操作

第二類操作是一元操作风钻,只有一個操作數(shù),即做源酒请,也作目的骡技。這個操作數(shù)可以是一個寄存器,也可以是一個存儲器位置羞反。比如說布朦,指令incl(%esp)會使棧頂元素加1。這種說法讓人想起C中的加1運算符(++)和減1運算符(--)

第三類是二元操作昼窗,第二個操作數(shù)既是源又是目的是趴。這種語法讓人想起C中像+=這樣的賦值運算符。注意澄惊,源操作數(shù)是第一個右遭,目的操作數(shù)時第二個做盅,這是不可交換操作持有的枚荣。例如指令subl %eax,%edx使寄存器%edx的值減去%eax中的值阅茶。第一個操作可以是立即數(shù),寄存器或存儲器位置畏吓。第二個操作數(shù)可以是寄存器或存儲器圍桌滚婉。不過movl指令一樣图筹,兩個操作數(shù)不能同時都是存儲器位置。

(c)位移操作

先給出位移量让腹,然后是待位移的值远剩,可以進(jìn)行算術(shù)或邏輯右移。移位量用單個字節(jié)編碼骇窍。位移量可以是一個立即數(shù)瓜晤,或者存放在單字節(jié)寄存器中%cl中。左移指令:sall,shll腹纳。兩者效果都一樣痢掠,都是將右邊填上0。右移指令sarl執(zhí)行算術(shù)移位(填上符號位
嘲恍,而shrl執(zhí)行邏輯位移(填上0)

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末足画,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子佃牛,更是在濱河造成了極大的恐慌淹辞,老刑警劉巖,帶你破解...
    沈念sama閱讀 221,198評論 6 514
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件俘侠,死亡現(xiàn)場離奇詭異象缀,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)爷速,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,334評論 3 398
  • 文/潘曉璐 我一進(jìn)店門攻冷,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人遍希,你說我怎么就攤上這事等曼。” “怎么了凿蒜?”我有些...
    開封第一講書人閱讀 167,643評論 0 360
  • 文/不壞的土叔 我叫張陵禁谦,是天一觀的道長。 經(jīng)常有香客問我废封,道長州泊,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 59,495評論 1 296
  • 正文 為了忘掉前任漂洋,我火速辦了婚禮遥皂,結(jié)果婚禮上力喷,老公的妹妹穿的比我還像新娘。我一直安慰自己演训,他們只是感情好弟孟,可當(dāng)我...
    茶點故事閱讀 68,502評論 6 397
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著样悟,像睡著了一般拂募。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上窟她,一...
    開封第一講書人閱讀 52,156評論 1 308
  • 那天陈症,我揣著相機(jī)與錄音,去河邊找鬼震糖。 笑死录肯,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的吊说。 我是一名探鬼主播论咏,決...
    沈念sama閱讀 40,743評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼疏叨!你這毒婦竟也來了潘靖?” 一聲冷哼從身側(cè)響起穿剖,我...
    開封第一講書人閱讀 39,659評論 0 276
  • 序言:老撾萬榮一對情侶失蹤蚤蔓,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后糊余,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體秀又,經(jīng)...
    沈念sama閱讀 46,200評論 1 319
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,282評論 3 340
  • 正文 我和宋清朗相戀三年贬芥,在試婚紗的時候發(fā)現(xiàn)自己被綠了吐辙。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 40,424評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡蘸劈,死狀恐怖昏苏,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情威沫,我是刑警寧澤贤惯,帶...
    沈念sama閱讀 36,107評論 5 349
  • 正文 年R本政府宣布,位于F島的核電站棒掠,受9級特大地震影響孵构,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜烟很,卻給世界環(huán)境...
    茶點故事閱讀 41,789評論 3 333
  • 文/蒙蒙 一颈墅、第九天 我趴在偏房一處隱蔽的房頂上張望蜡镶。 院中可真熱鬧,春花似錦恤筛、人聲如沸官还。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,264評論 0 23
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽妻枕。三九已至,卻和暖如春粘驰,著一層夾襖步出監(jiān)牢的瞬間屡谐,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 33,390評論 1 271
  • 我被黑心中介騙來泰國打工蝌数, 沒想到剛下飛機(jī)就差點兒被人妖公主榨干…… 1. 我叫王不留愕掏,地道東北人。 一個月前我還...
    沈念sama閱讀 48,798評論 3 376
  • 正文 我出身青樓顶伞,卻偏偏與公主長得像饵撑,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子唆貌,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,435評論 2 359

推薦閱讀更多精彩內(nèi)容