2017-01-24 3 views
2

Linux x86_x64에서 32 비트, 정적 및 공유 라이브러리를 여러 개 성공적으로 빌드 했으므로 이제이를 함께 실행 파일로 연결하려고합니다. 오류 :gcc 잘못된 버전 (최대) 오류 기호 추가 : 값이 잘못되었습니다.

/usr/bin/ld: foo.so: __moddi3: invalid version 21 (max 0) 

foo.so: error adding symbols: Bad value 
collect2: error: ld returned 1 exit status 

여기서 foo.so는 내가 만든 공유 라이브러리 중 하나입니다.

__moddi3 함수는 libgcc Integer Library Routines의 일부입니다. 서명은 다음과 같습니다 :

— Runtime Function: long __moddi3 (long a, long b) 

그리고 그 규칙은 32 비트 코드에 64 비트 산술을 제공하는 것입니다.

이 라이브러리 버전의 의미를 찾을 수 없습니다.

왜 라이브러리가 이미 빌드 된 후에이 오류가 표시됩니까?

나는 컴파일 및 링크하는 -fPIC-m32 플래그 모든 공유 libs와 내장.

실행 파일은 CXX 실행 파일입니다.

여기에 그래서 나는 해결책을 발견 --verbose

Using built-in specs. 
COLLECT_GCC=/usr/bin/c++ 
COLLECT_LTO_WRAPPER=/usr/lib/gcc/x86_64-linux-gnu/5/lto-wrapper 
Target: x86_64-linux-gnu 
Configured with: ../src/configure -v --with-pkgversion='Ubuntu 5.4.0-6ubuntu1~16.04.4' --with-bugurl=file:///usr/share/doc/gcc-5/README.Bugs --enable-languages=c,ada,c++,java,go,d,fortran,objc,obj-c++ --prefix=/usr --program-suffix=-5 --enable-shared --enable-linker-build-id --libexecdir=/usr/lib --without-included-gettext --enable-threads=posix --libdir=/usr/lib --enable-nls --with-sysroot=/ --enable-clocale=gnu --enable-libstdcxx-debug --enable-libstdcxx-time=yes --with-default-libstdcxx-abi=new --enable-gnu-unique-object --disable-vtable-verify --enable-libmpx --enable-plugin --with-system-zlib --disable-browser-plugin --enable-java-awt=gtk --enable-gtk-cairo --with-java-home=/usr/lib/jvm/java-1.5.0-gcj-5-amd64/jre --enable-java-home --with-jvm-root-dir=/usr/lib/jvm/java-1.5.0-gcj-5-amd64 --with-jvm-jar-dir=/usr/lib/jvm-exports/java-1.5.0-gcj-5-amd64 --with-arch-directory=amd64 --with-ecj-jar=/usr/share/java/eclipse-ecj.jar --enable-objc-gc --enable-multiarch --disable-werror --with-arch-32=i686 --with-abi=m64 --with-multilib-list=m32,m64,mx32 --enable-multilib --with-tune=generic --enable-checking=release --build=x86_64-linux-gnu --host=x86_64-linux-gnu --target=x86_64-linux-gnu 
Thread model: posix 
gcc version 5.4.0 20160609 (Ubuntu 5.4.0-6ubuntu1~16.04.4) 
COMPILER_PATH=/usr/lib/gcc/x86_64-linux-gnu/5/:/usr/lib/gcc/x86_64-linux-gnu/5/:/usr/lib/gcc/x86_64-linux-gnu/:/usr/lib/gcc/x86_64-linux-gnu/5/:/usr/lib/gcc/x86_64-linux-gnu/ 
LIBRARY_PATH=/usr/lib/gcc/x86_64-linux-gnu/5/32/:/usr/lib/gcc/x86_64-linux-gnu/5/../../../i386-linux-gnu/:/usr/lib/gcc/x86_64-linux-gnu/5/../../../../lib32/:/lib/i386-linux-gnu/:/lib/../lib32/:/usr/lib/i386-linux-gnu/:/usr/lib/../lib32/:/usr/lib/gcc/x86_64-linux-gnu/5/:/usr/lib/gcc/x86_64-linux-gnu/5/../../../i386-linux-gnu/:/usr/lib/gcc/x86_64-linux-gnu/5/../../../:/lib/i386-linux-gnu/:/lib/:/usr/lib/i386-linux-gnu/:/usr/lib/ 
COLLECT_GCC_OPTIONS='-g' '-m32' '-v' '-o' '../BIN/Y' '-L/home/X/W/Y/LibTee/lib/Linux' '-rdynamic' '-shared-libgcc' '-mtune=generic' '-march=i686' 
/usr/lib/gcc/x86_64-linux-gnu/5/collect2 -plugin /usr/lib/gcc/x86_64-linux-gnu/5/liblto_plugin.so -plugin-opt=/usr/lib/gcc/x86_64-linux-gnu/5/lto-wrapper -plugin-opt=-fresolution=/tmp/ccM5EczN.res -plugin-opt=-pass-through=-lgcc_s -plugin-opt=-pass-through=-lgcc -plugin-opt=-pass-through=-lc -plugin-opt=-pass-through=-lgcc_s -plugin-opt=-pass-through=-lgcc --sysroot=/ --build-id --eh-frame-hdr -m elf_i386 --hash-style=gnu --as-needed -export-dynamic -dynamic-linker /lib/ld-linux.so.2 -z relro -o ../BIN/Y /usr/lib/gcc/x86_64-linux-gnu/5/../../../../lib32/crt1.o /usr/lib/gcc/x86_64-linux-gnu/5/../../../../lib32/crti.o /usr/lib/gcc/x86_64-linux-gnu/5/32/crtbegin.o -L/home/X/W/Y/LibTee/lib/Linux -L/usr/lib/gcc/x86_64-linux-gnu/5/32 -L/usr/lib/gcc/x86_64-linux-gnu/5/../../../i386-linux-gnu -L/usr/lib/gcc/x86_64-linux-gnu/5/../../../../lib32 -L/lib/i386-linux-gnu -L/lib/../lib32 -L/usr/lib/i386-linux-gnu -L/usr/lib/../lib32 -L/usr/lib/gcc/x86_64-linux-gnu/5 -L/usr/lib/gcc/x86_64-linux-gnu/5/../../../i386-linux-gnu -L/usr/lib/gcc/x86_64-linux-gnu/5/../../.. -L/lib/i386-linux-gnu -L/usr/lib/i386-linux-gnu -rpath /home/X/W/Y/LibTee/lib/Linux:/home/X/W/Y/BIN -ltee ../openssl/Lib/Linux/libssl.a ../IPP_5_3_1_064/IA32/lib/Linux/libippcore.a ../IPP_5_3_1_064/IA32/lib/Linux/libippcp.a ../IPP_5_3_1_064/IA32/lib/Linux/libipps.a ../BIN/libCryptoDataGen.so -lgcc -lstdc++ -lm -lgcc_s -lgcc -lc -lgcc_s -lgcc /usr/lib/gcc/x86_64-linux-gnu/5/32/crtend.o /usr/lib/gcc/x86_64-linux-gnu/5/../../../../lib32/crtn.o 
/usr/bin/ld: ../BIN/libCryptoDataGen.so: __moddi3: invalid version 21 (max 0) 
../BIN/libCryptoDataGen.so: error adding symbols: Bad value 
collect2: error: ld returned 1 exit status 

답변

2

와 링커 출력입니다. 문제는 :

나는 foo.so. 공유 라이브러리를 만들었습니다. foo는 일부 정적 인 라이브러리와 연결되었습니다. 나는 그들 중 많은 수가 libgcc와 함께 __moddi3 함수 을 포함하고 있음을 발견했다.

저는 실행 바에 foo.so를 연결하려고했습니다. 막대는 또한 정적 라이브러리에 링크되어 있으며 많은 라이브러리에는 libgcc와 함께 __moddi3 함수가 포함되어 있습니다.

문제는 foo.so가 정적 라이브러리에서 가져온 심볼을 내 보낸 것이 었습니다. __moddi3 함수는 그 심볼들 중 하나였습니다. See here a detailed cover of the scenario. 따라서 어떤 일이 발생했는지는 실행 파일이 foo에서 내 보낸 __moddi3 함수 버전과 호환되지 않는 일부 libgcc 항목을 가져 와서 링커에서 __moddi3 버전을 발견했을 때 - 호환 가능하지 않은 링크를 시도하는 중 오류가 발생했습니다. 버전.

해결책은 이전 링크에서 제공됩니다. 이것을 처리하는 방법은 컴파일러에서 원하는 심볼을 내보내고 다른 모든 심볼을 숨기는 (와일드 카드 * 사용) 내보내기 목록을 사용하는 것입니다.
CMake를 사용하고 있으므로 -Wl,--version-script,exportmapset_target_properties(foo PROPERTIES LINK_FLAGS을 추가했습니다. 'exportmap'은 내 내보내기 목록 파일의 이름입니다. 그것은의 형식입니다 :

{ 
    global: 
     func_1; 
     func_2; 
     func_3; 
    local: 
     *; 
    } 

당신이 CMake는 메이크에 -Wl,--version-script,exportmapC_FLAGS에 또는 CXX_FLAGS를 추가 사용하지 않는 경우.

readelf -Ws foo.so을 사용하면 내보내기 기호 표를 볼 수 있습니다.

Here's another good read on the subject.

관련 문제