對編譯鏈接的整個過程和詳細的每個過程的認識

在windows下的開發環境是集成開發環境,編譯鏈接過程一鍵就可做到,而在linux下的操作都是離散的,對於編譯鏈接的認識是建立在linux環境基礎之上的;電腦只能識別二進制序列,而我們的代碼是利用c語言寫的,需要轉換位機器所能識別的二進制序列,編譯鏈接過程就是將代碼轉換成機器所能識別的二進制序列(目標文件)並生成可執行文件的過程。

整個過程爲:

1.預處理

在此步驟對代碼進行預處理:頭文件展開,宏替換,去註釋,條件編譯;

gcc -E test.c -o test.i

此命令是對test.c進行到預處理,並將處理結果放到test.i中。

2.c代碼轉換爲彙編;

gcc -S test.i -o tets.s

此命令是對test.i進行彙編轉換,並將彙編轉換結果放入test.s中。

3.彙編——>二進制;

gcc -c test.s -o test.o

此處test.o是目標文件,其中存放的是二進制序列;

4.鏈接 

鏈接所有二進制程序,生成可執行文件。

頭文件展開:展開爲頭文件所在的絕對地址,在linux下#include<stdio.h>展開爲"/usr/include/stdio.h" 

宏替換:出現宏標識符的位置,替換爲其定義式標識符後面的文本;

例:

#define PRINT printf("Replace\n")

int main()
{
	PRINT;
	
	return 0;
}
替換後爲:

#include<stdio.h>


#define PRINT printf("Replace\n")

int main()
{
	PRINT;
	
	return 0;
}

去註釋:在預處理階段,相當於直接將註釋的這部分代碼剔除掉,不出現在test.i文件中;

條件編譯:

在編譯程序時,使用條件編譯可以實現某條語句或某組語句進行編譯或者忽略;條件編譯常常用於調試程序;

條件編譯的基本結構爲:

#if    常量表達式   

  語句;

#endif

和if語句一樣也可以嵌套使用

如果常量表達式的值爲非零值(真),正常執行語句部分,否則這部分就像去掉註釋掉一樣,不出現在文件中;

#ifdef  MIN

語句;

#endif

如果MIN這個宏已被定義就執行語句部分,如果沒有定義,就刪除語句部分(即這部分不進行編譯);

例:

#include<stdio.h>
//#define DEBUG

int main()
{
	#ifdef DEBUG
		printf("DEBUG\n");
	#endif
	return 0;

}
DEBUG沒有被定義,在預處理時,將printf();語句刪除,即下面這樣:

int main()
{



 return 0;

}
若定義了DEBUG這個宏,在預處理後爲:

int main()
{

  printf("DEBUG\n");

 return 0;

}





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