CentOS: Использование GCC 4.7 из devtoolset приводит к некорректному связыванию libstdC++ (неопределенные символы)

Я использую devtoolset-1.0 для CentOS 6.3, чтобы временно обновить версию GCC. Хотя теперь я могу скомпилировать свое приложение на C++, в окончательном двоичном коде отсутствуют некоторые символы:

$ ldd -d -r myapp
$     [..]
$     libstdc++.so.6 => /usr/lib64/libstdc++.so.6 (0x0000003216e00000)
$     [..]
$ undefined symbol: _ZNSt8__detail15_List_node_base11_M_transferEPS0_S1_    (./myapp)
$ undefined symbol: _ZNSt8__detail15_List_node_base7_M_hookEPS0_      (./myapp)
$ undefined symbol: _ZNSt8__detail15_List_node_base9_M_unhookEv (./myapp)

Я выяснил, что это некоторые новые функции, которых нет в "старой" libstdC++, а в более новой libstdC++. В моей системе установлены как libstdC++ (версия по умолчанию 4.4.7), так и devtoolset-1.0-libstdC++-devel (4.7 через devtoolset). Интересно, что libstdC++ из devtoolset ссылается на старый:

$ cat /opt/centos/devtoolset-1.0/root/usr/lib/gcc/x86_64-redhat-linux/4.7.0/libstdc++.so
$ /* GNU ld script
$    Use the shared library, but some functions are only in
$    the static library, so try that secondarily.  */
$ OUTPUT_FORMAT(elf64-x86-64)
$ INPUT ( /usr/lib64/libstdc++.so.6 -lstdc++_nonshared )

На самом деле я хочу заменить привязку libstdC++, но я не знаю, как этого добиться. Я уже пытался установить LD_LIBRARY_PATH и указывать на каталог devtoolset, но libstdC++ все еще был установлен в старое местоположение. Также символическая ссылка не привела к успеху, потому что это скрипт ld, а не реальная разделяемая библиотека.

2 ответа

в финальном двоичном коде отсутствуют некоторые символы

Это похоже на ошибку в devtoolset-1-gccЯ полагаю, это было исправлено в более поздних версиях devtoolset.

Интересно, что libstdC++ из devtoolset ссылается на старый:

Да, именно так должен работать devtoolset gcc (см. Этот ответ для более подробной информации).

На самом деле я хочу заменить привязку libstdC++, но я не знаю, как этого добиться.

Вы не можете сделать это с devtoolset GCC, потому что он даже не имеет нового libstdc++.so библиотека. Как вы обнаружили, этот файл на самом деле является скриптом компоновщика, который связывает ваш двоичный файл с libstdc++_nonshared.a /usr/lib64/libstdc++.so

Так как нет нового libstdc++.so Вы не можете ссылаться на него.

Компилятор GCC и его библиотеки (очень специально g++ и соответствующий libstdc++ время выполнения) должны соответствовать. Компиляция с более новым компилятором (очень часто, практически гарантируется, если поддерживается новая версия языка) дает двоичные файлы, которые не работают со старой библиотекой. Старые двоичные файлы могут работать с более новой библиотекой, здесь нет никаких гарантий.

Другие вопросы по тегам