在前面的<<程序員的自我修養 鏈接 裝載與庫>>關於object files的內容中,有看到使用自定義段的部分內容,
(如果關於object files的內容不了解的話,可以去參考<<程序員的自我修養 鏈接 裝載與庫>>這本書或者去wiki,
其中也有關於段的解釋,也可以稱作節區.) 可以通過硬編碼實現自定義段.
__attribute__ ((section("name"))) .....
編譯生成的object file,代碼會保存在".text"段,全局變量和靜態變量會放在".data"和".bss"(未初始化的全局變量和局部靜態變量)
利用GCC的擴展機制就可以做到自定義段了.
對[ __attribute__ ] 很感興趣,下面來看一個不一樣的HelloWorld程序:
#include <stdio.h> #include <stdlib.h> static __attribute__((constructor)) void before() { printf("Hello"); } static __attribute__((destructor)) void after() { printf(" World!\n"); } int main(int args,char ** argv) { return EXIT_SUCCESS; }
我們知道這是一個HelloWorld程序,所以輸出的結果就是"Hello World!",很簡單,不需要對這點過多關心.
下面我們來關心關心別的:
__attribute__((constructor)) __attribute__((destructor))
解釋一下:__attribute__((constructor)) 在main() 之前執行,__attribute__((destructor)) 在main()執行結束之后執行.
上面的例子中我沒有在main函數中添加任何的輸出,所以看不到具體的信息.這點可以自己嘗試~
如果要在main()之前或者是執行完成之后,需要執行很多的前處理動作或者是后處理動作,我們應該怎么處理?
也許,你需要下面這些東西:
__attribute__((constructor(PRIORITY))) __attribute__((destructor(PRIORITY)))
PRIORITY: 優先級.
好吧,下面就來試試:
執行的輸出如下:
從輸出的信息看,前處理都是按照優先級先后執行的,而后處理則是相反的,好吧,我們使用GDB調試驗證一下:
從調試的信息也是驗證了上面的結果.
另外一個問題,優先級有沒有范圍的?
其實剛開始我寫的程序中的優先級是1,我們將上面的程序改一下,然后編譯看一下會有什么樣的結果:
0-100(包括100),是內部保留的,所以在編碼的時候需要注意.
關於__attribute__的用法,可以有另外一種寫法,先聲明函數,然后再定義.
glibc多采用第一種寫法.
外面又下雨了~ Cause i am ur lady, u are my man.