Символы стандартной библиотеки C ++, связанные во время выполнения с другими библиотеками - PullRequest
0 голосов
/ 08 апреля 2020

У меня есть приложение C ++, созданное с помощью G CC 8.3 на RHEL 6 и связанное с кучей внутренних и внешних общих библиотек.

Я пытаюсь понять, как загрузчик связывает символы моего приложения во время выполнения .

То, что я наблюдал, и я не могу понять, почему некоторые символы из libstdc ++. Поэтому отображаются в мое приложение и общие библиотеки:

LD_DEBUG=bindings ldd -r main
[...]
binding file /usr/lib64/libstdc++.so.6 [0] to ./libshared01.so [0]: normal symbol `std::__detail::_Prime_rehash_policy::_M_next_bkt(unsigned long) const' [GLIBCXX_3.4.18]
binding file /usr/lib64/libstdc++.so.6 [0] to ./libshared02.so [0]: normal symbol `std::_Hash_bytes(void const*, unsigned long, unsigned long)' [CXXABI_1.3.5]
binding file /usr/lib64/libstdc++.so.6 [0] to ./libshared03.so [0]: normal symbol `char* std::basic_string<char, std::char_traits<char>, std::allocator<char> >::_S_construct<__gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > > >(__gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, __gnu_cxx::__normal_iterator<char*, std::basic_string<char, std::char_traits<char>, std::allocator<char> > >, std::allocator<char> const&, std::forward_iterator_tag)' [GLIBCXX_3.4.14]
binding file /usr/lib64/libstdc++.so.6 [0] to ./libshared03.so [0]: normal symbol `char* std::basic_string<char, std::char_traits<char>, std::allocator<char> >::_S_construct<char const*>(char const*, char const*, std::allocator<char> const&, std::forward_iterator_tag)' [GLIBCXX_3.4.14]
binding file /usr/lib64/libstdc++.so.6 [0] to ./libshared04.so [0]: normal symbol `std::__future_base::_Async_state_common::~_Async_state_common()' [GLIBCXX_3.4.17]
binding file /usr/lib64/libstdc++.so.6 [0] to ./main [0]: normal symbol `std::basic_stringbuf<char, std::char_traits<char>, std::allocator<char> >::~basic_stringbuf()' [GLIBCXX_3.4]

Не все стандартные символы связаны вне libstdc ++. поэтому , но только несколько, все остальные отображаются так, как я ожидал:

binding file /usr/lib64/libstdc++.so.6 [0] to /usr/lib64/libstdc++.so.6 [0]: normal symbol `std::terminate()' [GLIBCXX_3.4]
binding file /usr/lib64/libstdc++.so.6 [0] to /usr/lib64/libstdc++.so.6 [0]: normal symbol `std::basic_ostream<char, std::char_traits<char> >& std::basic_ostream<char, std::char_traits<char> >::_M_insert<double>(double)' [GLIBCXX_3.4.9]
binding file /usr/lib64/libstdc++.so.6 [0] to /usr/lib64/libstdc++.so.6 [0]: normal symbol `std::basic_ostream<wchar_t, std::char_traits<wchar_t> >::sentry::~sentry()' [GLIBCXX_3.4]

Я не использую какие-либо флаги видимости из G CC или атрибуты видимости в моем коде.

Однако я предполагал, что все эти символы, четко определенные как стандартные, будут сопоставлены с libstdc ++., Поэтому по умолчанию.

Моя основная проблема заключается в том, что поведение / производительность моего приложения, таким образом, случайно зависят от процесса отображения символов, который я не контролирую. Если одна из моих внешних зависимостей сильно оптимизирована, и все стандартные строковые символы моего приложения внезапно выбираются из этой внешней библиотеки, это выглядит как проблема.

Может кто-то пролить свет на это поведение? Это ожидается и задокументировано?

1 Ответ

0 голосов
/ 08 апреля 2020

Однако я предполагал, что все эти символы, четко определенные как стандартные, будут сопоставлены с libstdc ++., Поэтому по умолчанию.

Почему? Многие из символов, которые вы просматриваете, являются шаблонами и создаются компилятором при сборке. Они могут не существовать в libstdc ++. [Некоторые специализации, такие как (скажем) std::basic_string<char, std::char_traits<char>, std::allocator<char>>], могут быть созданы в dylib для экономии места в вашем приложении; но, конечно, не все из них.

Вы можете получить список символов, экспортируемых из libstdc ++., используя nm -g (если я правильно помню). Некоторые версии nm также имеют флаг -demangle. Вы, вероятно, будете удивлены содержанием этого списка.

...