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++
время выполнения) должны соответствовать. Компиляция с более новым компилятором (очень часто, практически гарантируется, если поддерживается новая версия языка) дает двоичные файлы, которые не работают со старой библиотекой. Старые двоичные файлы могут работать с более новой библиотекой, здесь нет никаких гарантий.