鏈結是將各種**和資料片段收集並組合成為乙個單一檔案的過程,這個檔案可以被載入(複製)到記憶體並執行。鏈結可以執行於編譯時,也就是在源**被翻譯成機器**時;也可以執行於載入時,也就是在程式被載入器載入到記憶體並執行;甚至執行於執行時,也就是應用程式來執行。首先:我們要了解目標檔案
目標檔案有三種形式:我們再來了解可重定位目標檔案:
我們以典型的elf可重定位目標檔案舉例,下面是elf檔案的格式:
elf頭
.text
.rodata
.data
.bss
.symtab
.ral.text
.rel.data
.debug
.line
.strtab
節頭部表
其中:
包括16位元組的標識資訊、檔案型別(.o,exec,.so)、機器型別(如intel 80386)、節頭表的偏移、節頭表的表項大小及表項個數。
編譯後的**部分。
唯讀資料,如 printf用到的格式串、switch跳轉表等。
已初始化的全域性變數和靜態變數。
未初始化全域性變數和靜態變數,僅是佔位符,不佔據任何磁碟空間。區分初始化和非初始化是為了空間效率。
存放函式和全域性變數(符號表)的資訊,它不包括區域性變數。
.text節的重定位資訊,用於重新修改**段的指令中的位址資訊。
.data節的重定位資訊,用於對被模組使用或定義的全域性變數進行重定位的資訊。
除錯用的符號表(gcc -g)
包含 .symtab節和 .debug節中的符號及節名
包含每個節的節名在.strtab節中的偏移、節的偏移和節的大小.接下來我們看下符號和符號表:
符號就是其實程式中的變數名、函式名。
注意:區域性變數temp分配在棧中,不會在函式外部被引用,因此不是符號定義。
符號定義的本質是:指被分配了儲存空間。如果是函式名則指**所在區;如果是變數名則指其所在的靜態資料區。所有定義的符號的值就是其目標所在的首位址。
全域性符號的強、弱全域性符號有強、弱的特性。鏈結器對符號的解析規則符號解析時,只能有乙個確定的定義(即每個符號僅佔一處儲存空間)。
所以,如果碰到符號存在多重定義時,就得有相應的處理規則:
強符號只能被定義一次,否則鏈結錯誤。C 獲取計算機內部資訊
computerinfohelper.cs 計算機資訊助手類 public class computerinfohelper catch exception e managementbaseobjectpropertyname.cs namespace wen.helpers.common.comp...
C 獲取計算機內部資訊
computerinfohelper.cs 計算機資訊助手類 public class computerinfohelper catch exception e managementbaseobjectpropertyname.cs namespace wen.helpers.common.comp...
計算機內部數字的儲存 擴充套件
在對精度要求很高的系統中,或要對小數的運算結果進行比較時,需要特別謹慎 js中的小數運算是精確的嗎?不一定js中的整數運算是精確的嗎?不一定js中表示的整數是連續的嗎?不是,當 js 的數字很大的時候,不再連續 js中表示的最大數字是多少?最大連續整數 從1開始數到這個數字一直都是連續的,並且到下乙...