2017-11-10 2 views
0

부스트를 사용하는 타사 라이브러리에 연결하려고합니다. 내가 올바른 부스트 라이브러리 (libboost_program_options.a)에 연결했지만 여전히 그것을 찾지 못했습니다.정의되지 않음 부스트 참조

오류 MSG는 (명확성을 위해 약간의 형식) :

undefined reference to `boost::program_options::validate(boost::any&, 
           std::vector<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >, std::allocator<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > > const&, 
           std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> >*, 
           int)' 

나노 --demangle libboost_program_options.a | grep validate

boost::program_options::validate(boost::any&,         std::vector<std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> >, std::allocator<std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> > > > const&, 
            bool*, 
            int) 
boost::program_options::validate(boost::any&, 
            std::vector<std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> >, std::allocator<std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> > > > const&, 
            std::string*, 
            int) 
boost::program_options::validate(boost::any&, 
            std::vector<std::string, std::allocator<std::string> > const&, 
            bool*, 
            int) 
boost::program_options::validate(boost::any&, 
            std::vector<std::string, std::allocator<std::string> > const&, 
            std::string*, 
            int) 

두 번째 레코드는 비슷하지만 외관상으로는 충분히 근접하지 않습니다. Boost를 컴파일하여 라이브러리에있는 내용과 일치하는 서명을 얻으려면 어떻게해야할까요? 라이브러리 소유자가 Boost의 어떤 버전을 사용 중인지 확인해 달라는 요청을 받았지만 아직 회신하지 않았습니다.

g ++ 버전 4.8.5를 사용하는 CentOS 7 상자에 있습니다. 하지만 내가 연결하려고하는 라이브러리는 C++ 11을 많이 사용하고 g ++ 6.1로 컴파일 되었기 때문에 devtoolset-6를 설치하면 g ++ 6 환경 (g ++ 6.3.1)을 얻을 수 있습니다. (g ++ 버전 6.3.1)

다운로드했습니다. Boost를 처음부터 (v1.65.1) 빌드하여 시스템 버전이 아닌 동일한 컴파일러로 빌드하십시오.

편집 ... John Zwinck는 올바른 방향으로 가고 있다고 생각하지만 새로운 ABI로 컴파일 할 수있는 부스트 라이브러리를 얻을 수 없습니다.

유효성 검증() 기능은 기본으로 아래로 빌드를 스트리핑 value_semantic.cpp

에서 발견하고, 추가 플래그는 설명 :

g++ -std=c++11 -D_GLIBCXX_USE_CXX11_ABI -c -o test.o libs/program_options/src/value_semantic.cpp 

nm --demangle test.o | grep validate 
00000000000008b6 T boost::program_options::validate(boost::any&, std::vector<std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> >, std::allocator<std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> > > > const&, bool*, int) 
0000000000000c02 T boost::program_options::validate(boost::any&, std::vector<std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> >, std::allocator<std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> > > > const&, std::string*, int) 
00000000000005f2 T boost::program_options::validate(boost::any&, std::vector<std::string, std::allocator<std::string> > const&, bool*, int) 
0000000000000b9a T boost::program_options::validate(boost::any&, std::vector<std::string, std::allocator<std::string> > const&, std::string*, int) 

이 매크로 _GLIBCXX_USE_CXX11_ABI는 GCC 5.1 사용할 수 있습니까?

+1

부스트 빌드에'g ++ -std = C++ 11'을 사용해 보셨나요? – burlyearly

+0

아니요 - 제가 아는 한 g ++ v6의 기본값은 C++ 11입니다. 나는 그것에 대해 생각하고 있었는데, Boost 빌드 시스템으로 그것을 가져 오는 방법을 알아야했습니다. – CoAstroGeek

+1

그냥 보았습니다. ccc 14가 gcc v6의 기본값입니다. https://gcc.gnu.org/projects/cxx-status.html#cxx11 – CoAstroGeek

답변

0

당신이 C++ 11 std::string에 대한로 충돌 GCC 듀얼 ABI의 실행 한 나타납니다

std::__cxx11::basic_string<char>* 

를 사용하여 API에 대한 연결을 시도 https://gcc.gnu.org/onlinedocs/libstdc++/manual/using_dual_abi.html

여러분의 프로그램 그러나 부스트 라이브러리가

std::basic_string<char>* 

이는 Boost 라이브러리가 5.1 이전의 GCC로 작성되었거나 새로운 ABI가 꺼진 상태로 작성되었음을 의미합니다. 두 경우 모두, 새 ABI와 자신의 코드는이 컴파일러 플래그를 추가하여 해제 컴파일 할 수 있습니다 : 그와 함께 프로그램을 컴파일하여

-D_GLIBCXX_USE_CXX11_ABI=0 

를, 시스템 제공 (기존 ABI)를 사용하는 것이 가능할 것이다 라이브러리를 향상시킵니다. 그렇다면 C++ ABI가 자신의 코드를 컴파일 한 업체 (라이브러리에 __cxx11를 요청하십시오)를 질문 할 것입니다.

+0

이것이 올바른 방향이라고 생각하지만, 제 3 자 라이브러리 ABI와 일치하도록 빌드를 얻을 수 없다. 위의 편집을 참조한다. 감사! – CoAstroGeek

0

좋아, 왜 g ++에서 cxx11 서명 (새 ABI)을 생성 할 수 없는지 알았습니다.

나는 -v 옵션을 g ++ 실행하는 경우 :

g++ -v 
Using built-in specs. 
COLLECT_GCC=g++ 
COLLECT_LTO_WRAPPER=/opt/rh/devtoolset-6/root/usr/libexec/gcc/x86_64-redhat-linux/6.3.1/lto-wrapper 
Target: x86_64-redhat-linux 
Configured with: ../configure --enable-bootstrap --enable-languages=c,c++,fortran,lto --prefix=/opt/rh/devtoolset-6/root/usr --mandir=/opt/rh/devtoolset-6/root/usr/share/man --infodir=/opt/rh/devtoolset-6/root/usr/share/info --with-bugurl=http://bugzilla.redhat.com/bugzilla --enable-shared --enable-threads=posix --enable-checking=release --enable-multilib --with-system-zlib --enable-__cxa_atexit --disable-libunwind-exceptions --enable-gnu-unique-object --enable-linker-build-id --enable-plugin --with-linker-hash-style=gnu --enable-initfini-array --disable-libgcj --with-default-libstdcxx-abi=gcc4-compatible --with-isl=/builddir/build/BUILD/gcc-6.3.1-20170216/obj-x86_64-redhat-linux/isl-install --enable-libmpx --enable-gnu-indirect-function --with-tune=generic --with-arch_32=i686 --build=x86_64-redhat-linux 
Thread model: posix 
gcc version 6.3.1 20170216 (Red Hat 6.3.1-3) (GCC) 

참고 분야 "구성"에서 다음을

--with-기본-libstdcxx-ABI =으로 gcc4 호환

이것이 의미하는 바는 g ++의 devtoolset-6 버전은 구식 ABI가 "구워진"스타일로 만들어 졌으므로 _GLIBCXX_USE_CXX11_ABI 매크로에 응답하지 않는다는 것입니다. 이 링크에 따르면

: https://gcc.gnu.org/onlinedocs/libstdc++/manual/configure.html

--with-기본-libstdcxx-ABI = OPTION 는 _GLIBCXX_USE_CXX11_ABI 매크로 (매크로 참조)에 대한 기본 값을 설정합니다. 기본값은 매크로를 1로 설정하는 OPTION = new이며 OPTION = gcc4 호환을 사용하여 0으로 설정합니다.이 옵션은 라이브러리 ABI를 변경하지 않습니다.

_GLIBCXX_USE_CXX11_ABI의 기본값 만 변경하는 것처럼 보일 수 있지만 _GLIBCXX_USE_CXX11_ABI 설정은 아무런 효과가 없습니다.

이 점에 긍정적이지는 않지만 지금은 내 실무 이론입니다. 추가 통찰력을 부탁드립니다.

관련 문제