<menu id="w8yyk"><menu id="w8yyk"></menu></menu>
  • <dd id="w8yyk"><nav id="w8yyk"></nav></dd>
    <menu id="w8yyk"></menu>
    <menu id="w8yyk"><code id="w8yyk"></code></menu>
    <menu id="w8yyk"></menu>
    <xmp id="w8yyk">
    <xmp id="w8yyk"><nav id="w8yyk"></nav>
  • 網站首頁 > 物聯資訊 > 技術分享

    Linux下gcc編譯控制動態庫導出函數小結

    2016-09-28 00:00:00 廣州睿豐德信息科技有限公司 閱讀
    睿豐德科技 專注RFID識別技術和條碼識別技術與管理軟件的集成項目。質量追溯系統、MES系統、金蝶與條碼系統對接、用友與條碼系統對接

    根據說明文檔“How To Write Shared Libraries"介紹,

    有四種方法:

    1. 在方法聲明定義時,加修飾:__attribute__((visibility("hidden")))

    就是說將不公開的函數都加上這個屬性,沒加的就是可見的

     

    2. gcc 在鏈接時設置 -fvisibility=hidden,則不加 visibility聲明的都默認為hidden; gcc默認設置 -fvisibility=default,即全部可見;

    在gcc中加了這個設置之后表示所有的函數都是對外不可見了,然后在代碼里面對于想公開的函數加上 __attribute__((visibility("default")))

     

    3. 使用export map,gcc -Wl,--version-script=export.map, 在export.map中指定

    {

    global:export_func;

    local:*;

    };

    則除了export_func外,全部為內部可見;

     

    4. 使用libtool的export-symbols選項,沒試過,略;

     

    以上方法,對于gcc的visibility功能需要 gcc 4以上版本,

    常見的宏,用于等同于 windows下的 __declspec(dllexport)(摘自:http://gcc.gnu.org/wiki/Visibility):

    #if defined _WIN32 || defined __CYGWIN__
    
      #ifdef BUILDING_DLL
    
        #ifdef __GNUC__
    
          #define DLL_PUBLIC __attribute__((dllexport))
    
        #else
    
          #define DLL_PUBLIC __declspec(dllexport) // Note: actually gcc seems to also supports this syntax.
    
        #endif
    
      #else
    
        #ifdef __GNUC__
    
          #define DLL_PUBLIC __attribute__((dllimport))
    
        #else
    
          #define DLL_PUBLIC __declspec(dllimport) // Note: actually gcc seems to also supports this syntax.
    
      #endif
    
      #define DLL_LOCAL
    
    #else
    
      #if __GNUC__ >= 4
    
        #define DLL_PUBLIC __attribute__ ((visibility("default")))
    
        #define DLL_LOCAL  __attribute__ ((visibility("hidden")))
    
      #else
    
        #define DLL_PUBLIC
    
        #define DLL_LOCAL
    
      #endif
    
    #endif
    
    
    
    實踐中發現幾個有意思的東西[實驗環境為ubuntu 9.10, gcc 4.4.1]:
    
    1. gcc -fvisibility=hidden 只在鏈接時傳入的.c文件起作用,對.o文件不其作用;
    
    比如test.c test1.c, 使用以下命令:
    
    gcc -shared -fvisibility=hidden -o test.so test.c test1.c
    
    和命令
    
    gcc -c test.c test1.c
    
    gcc -shared -fvisibility=hidden -o test.so test.o test1.o
    
    生成的test.so中的對應可見性是不一樣的, 使用“readelf -s test.so”查看發現:
    
    第一個達到預期目的,即將兩個.c文件中的functions設為HIDDEN,
    
    而第2個則不行,-fvisibility=hidden不起作用;
    
    再用gcc -shared -fvisibility=hidden -o test.so test.o test1.c
    
    生成的so,則可發現test1.c中的函數為HIDDEN,但test.o中的函數仍為DEFAULT;
    
    
    
    2. 實驗通過export map的方法,通過readelf總是發現函數仍然可見,后來搜索發現:
    
    需同時使用ld --retain-symbols-file --version-script 兩個選項方能達到 使得elf文件中的.dynsym和.symtab
    
    中的符號表都得到控制;其中--retain-symbols-file控制靜態符號表,--version-script則對應dynamic符號表;
    另外可以參考 http://blog.csdn.net/shuiyingzi5/article/details/8108190
    
    
    
    
    轉自 http://blog.csdn.net/zdragon2002/article/details/6061962
    RFID管理系統集成商 RFID中間件 條碼系統中間層 物聯網軟件集成
    最近免费观看高清韩国日本大全