理解程序的一般結構

1、程序的段

程序由不同的段構成(代碼段,數據段)

       - 程序的靜態特徵就是指令和數據

       - 程序的動態特徵就是執行指令處理數據

程序文件的一般佈局 

                                                         程序文件未運行時

代碼段(.text)

       - 源代碼中的可執行語句編譯後進入代碼段

       - 代碼段在有內存管理單元的系統中具有只讀屬性

       - 代碼段的大小在編譯結束後就已經固定(不能動態改變)

       - 代碼段中可以包含常量數據(如:常量字符串)

數據段(.data,.bss,.rodata)

       - 數據段用於存放源代碼中具有全局生命期的變量

            ★ .bss:存儲未初始化(初始化爲0)的變量

            ★ .data:存儲具有非0初始值的變量,有時也會將字符串常量放這裏

            ★ .rodata:存儲const關鍵字修飾的變量,字符串常量

注:.bss段只是爲未初始化的全局變量和局部靜態變量預留位置而已,它並沒有內容,所以它在文件中不佔空間

 

面試中的小問題 

       同是全局變量靜態變量,爲什麼初始化的和未初始化的保存在不同段中?

答:程序加載後,.bss段中的所有內存單元被初始化爲0,將程序文件中.data段相關的初始值寫入對應內存單元

編程實驗

關鍵段的分析 test.c

int dt_main()
{
    return 0;
}

char g_no_value;

int g_value = 1;

char g_str[] = "wss";
const int g_c = 3;

int dt_main()
{
	static char c_no_value;

	static int c_value = 2;

	return 0;
}

                         通過objdump,可以看到.data段對應變量的值

2、堆、棧、內存映射段

程序中的棧

       - 程序中棧的本質是一片連續的內存空間

       - SP寄存器作爲棧頂“指針”實現入棧操作和出棧操作

棧的深入理解

       - 中斷髮生時,棧用於保存寄存器的值

       - 函數調用時,棧用於保存函數的活動記錄(棧幀信息)

       - 併發編程時,每一個線程擁有自己獨立的棧

程序中的堆(Heap)

       - 堆是一片“閒置"的內存空間,用於提供動態內存分配

       - 堆空間的分配需要函數支持(malloc)

       - 堆空間在使用結束後需要歸還(free)

內存映射段(Memory Mapping Segment)

       - 內核將硬盤文件的內容直接映射到內存映射段(mmap)

       - 動態鏈接庫在可執行程序加載時映射到內存映射段

       - 程序執行時能夠創建匿名映射區存放程序數據

內存映射文件原理簡介

       - 將硬盤上的文件數據邏輯映射到內存中(零耗時)

       - 通過缺頁中斷進行文件數據的實際載入(一次數據拷貝)

       - 映射後的內存的讀寫就是對文件數據的讀寫

 

地址空間分佈圖

           0~0x08048000是操作系統使用的,中間空白區域是因爲堆,棧,內存映射段的起始地址是隨機的(爲了安全)

 

3、小結

各個段的作用 

                 - 堆棧段在程序運行後才正式存在,是程序運行的基礎 

                 - .bss段存放的是未初始化的全局變量和靜態變量 

                 - .text段存放的是程序中的可執行代碼 

                 - .data段保存的是已經初始化了的全局變量和靜態變量 

                 - .rodata段存放程序中的常量值

程序術語的對應關係 

                 - 靜態存儲區通常指程序中的.bss.data段 

                 - 只讀存儲區通常指程序中的.rodata段 

                 - 局部變量所佔空間爲上的空間 

                 - 動態空間中的空間 

                 - 程序可執行代碼存放於.text

小結

                 - 程序編碼在編譯後對應可執行程序中的不同存儲區 

                 - 程序和進程不同,程序靜態概念進程是動態概念 

                 - 堆棧段是程序運行的基礎,只存在於進程空間中 

                 - 程序可執行代碼存放於.text段,是只讀的 

                 - .bss.data段用於保存全局變量靜態變量 

 

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