/usr/bin/ld:
.gnu.linkonce.t._ZSt18uninitialized_copyIN9__gnu_cxx17__normal_iteratorIPKN5boost7variantINS2_8weak_ptrIvEENS2_8s
.gnu.linkonce.r._ZSt18uninitialized_copyIN9__gnu_cxx17__normal_iteratorIP
ignals26detail21foreign_void_weak_ptrENS2_6detail7variant5void_ESB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_EESt6vectorI
SC_SaISC_EEEEPSC_ET0_T_SL_SK_' referenced in section
KN5boost7variantINS2_8weak_ptrIvEENS2_8signals26detail21foreign_void_weak_ptrENS2_6detail7variant5void_ESB_SB_SB_SB_SB_SB_SB_SB
SB_SB_SB_SB_SB_SB_SB_SB_SB_EESt6vectorISC_SaISC_EEEEPSC_ET0_T_SL_SK’ of ../fancirclese/libfancirclese.a(fancirclese_dump_thre
ad.o): defined in discarded section `.gnu.linkonce.t._ZSt18uninitialized_copyIN9__gnu_cxx17__normal_iteratorIPKN5boost7variantI
NS2_8weak_ptrIvEENS2_8signals26detail21foreign_void_weak_ptrENS2_6detail7variant5void_ESB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_SB_S
B_SB_SB_SB_EESt6vectorISC_SaISC_EEEEPSC_ET0_T_SL_SK_’ of ../fancirclese/libfancirclese.a(fancirclese_dump_thread.o)
以上是我遇到的編譯warning
經網上搜索發現這是gcc編譯器引入後COMDAT section(或者叫linkonce section)纔會出現的。
COMDAT section簡單地說就是編譯器將可能存在多處定義的symbol(c++模板、inline函數等)作了一個特殊處理,放到了一個特殊的section,這樣多個object文件的COMDAT section可能保存了同一個symbol的信息,在linker選擇symbol進行讀取的時候只會選擇其中一個section,而丟棄其他secition。
如果由於鏈接順序不對,導致引用了不對的section(即被丟棄的那個),就會報這個錯。(不同的編譯參數,如-g -pipe -W -Wall -fPIC -O2,可能導致這個問題)
爲解決這個問題,需要統一編譯參數,並檢查鏈接順序(按照鏈接參數從左向右鏈接)。
以上的warning經排查就是因爲鏈接的某一個庫的編譯參數與其他模塊不同,少了-O2
還有一種warning:
/usr/bin/ld:
.gnu.linkonce.t._ZN5boost8signals25slot0IvNS_8functionIFvvEEEED1Ev' referenced in section
.gnu.linkonce.r._ZN5boost8signals25slot0IvNS_8functionIFvvEEEED1Ev’ of ./libut_doraemon.a(ut_doraemon_city_id_data_handler.o): defined in discarded section `.gnu.linkonce.t._ZN5boost8signals25slot0IvNS_8functionIFvvEEEED1Ev’ of ./libut_doraemon.a(ut_doraemon_city_id_data_handler.o)
這個warning是因爲一個模板類的T類型在定義的時候,顯示定義了析構函數,導致引用了不同的基類。