編譯的過程(gcc -c 作了什麼)

gcc -c hello.c 背後

#include<stdio.h>
int main()
{
  printf("Hello World\n");
  return 0;
}
gcc hello.c -o hello.o
./hello.o
Hello World
  • 上述過程能夠分爲四個部分:預處理、編譯、彙編和連接
  1. 預編譯和編譯處理程序:cc1
  2. 彙編器處理程序:as
  3. 連接器處理程序:ld
  • 預編譯(cc1)
  1. 刪除
  2. 展開
  3. 添加
  4. 保留

gcc -E hello.c -o hello.ic++

  • 編譯(cc1) gcc -S hello.c -o hello.s緩存

  • 彙編(as) gcc -c hello.s -o hello.o 或者as hello.s -o hello.o函數

  • 連接(ld)設計

靜態語言c/c++模塊之間通訊的方式

模塊間的函數調用和模塊間的變量的訪問,函數訪問必須知道目標函數的地址,變量訪問也必須知道目標變量的地址,因此這兩種方式均可以歸結爲同一種方式,那就是模塊間的符號的引用。模塊的拼接就引出了連接。 連接code

  1. 目的:將各個模塊之間相互引用的部分都處理好,使得各個模塊之間可以正確地銜接。
  2. 過程:連接過程分爲兩步,第一步是合併全部目標文件的段,並調整段偏移和段長度,合併符號表,分配內存地址;第二步是連接的核心,進行符號的重定位

數據

  • 數據存放的區域有三個地方:.data段、.bss段和.text段。通常C語言的編譯後執行語句都編譯成機器代碼,保存在.text段;對於初始化不爲0的全局變量和靜態變量存放在.data段;對於未初始化或者初始化值爲0的段存放在.bss段中,並且不佔目標文件的空間。
  1. 文本段:只讀、可共享、程序源代碼編譯後的機器指令、爲防止堆棧溢出存放在堆或者堆棧的下方
  2. 初始化數據段:不是隻讀,變量的值在運行時能夠修改
  3. 未初始化數據段
  • 數據和指令分開的好處
  1. 防止指令被修改,數據段可讀寫,指令段只讀,被分別映射到不一樣的虛擬存儲區
  2. CPU的緩存被設計成數據緩存和指令緩存
  3. 文本段是可共享的,便可執行的指令是共享的,對於頻繁執行的程序只須要一個副本在內存中就能夠了;而數據段倒是每一個進程私有的;這樣作能夠大量節省內存。
相關文章
相關標籤/搜索