pthread в glibc.so реализован слабым символом для обеспечения функций заглушки pthread?
Является pthread
в glibc.so
осуществляется слабым символом, чтобы обеспечить pthread
функции заглушки?
Я знаю, что есть pthread.so
обеспечить функции, аналогичные pthread
в glibc.so
кто-то сказал pthread
в glibc
предоставить только заглушку и будет заменен при явной ссылке на lpthread
,
Итак, мой вопрос, как это поддержать? используя слабый символ или другие технологии?
является libssl
похоже на pthread
в glibc
?
2 ответа
Да, glibc использует реализацию-заглушку различных функций pthread, так что однопоточные программы не должны тратить циклы, выполняя такие вещи, как блокировка и разблокировка мьютексов, и, тем не менее, не должны связываться с другой библиотекой C (как это делается в Мир Microsoft, например).
Например, согласно POSIX, каждый раз, когда вы звоните fputc(ch, stream)
Есть мьютекс блокировки и разблокировки. Если вы этого не хотите, звоните fputc_unlocked
, Но когда вы делаете это, вы используете расширение POSIX, связанное с многопоточностью; это не подходящий обходной путь для программ, которые не используют POSIX или не используют API потоков.
Переопределение функций заглушки pthread на реальные (в динамическом glibc) не основано на слабых символах. Механизм разделяемой библиотеки позволяет переопределять неслабые определения.
Слабые символы - это механизм, который позволяет переопределять символы при статическом связывании.
Если вам нужен источник для приведенного выше утверждения, вот оно:
"Обратите внимание, что слабое определение в DSO не имеет никакого эффекта. Слабые определения играют роль только в статическом связывании". Ульрих Дреппер, "Как писать общие библиотеки".
Если вы бежите nm
на статическом glibc в вашей системе (если он у вас есть), libc.a
, вы заметите, что функции, такие как pthread_mutex_lock
отмечены слабыми. В динамической версии libc.so.<whatetever>
функции не отмечены как слабые.
Примечание: вы должны использовать nm -D
или же nm --dynamic
смотреть на символы в общей библиотеке. nm
не будет производить ничего в разделяемой библиотеке, которая будет удалена. Если это так, вы смотрите на символы отладки, а не на динамические символы.
Смотрите этот так ответ. Можно использовать несколько методов, позволяющих определять один и тот же символ в нескольких библиотеках, с которыми связана программа, в зависимости от того, используется ли динамическое или статическое связывание.
Взаимосвязь символов. При динамическом связывании, если символ определен в нескольких библиотеках, компоновщик будет использовать первую найденную версию (если символы не являются внутренними, скрытыми или защищенными; см. Описание в этой статье блога)
Слабые объекты. При статическом связывании, если компоновщик находит два символа с одинаковым именем и один из них является "слабой" ссылкой, тогда компоновщик будет использовать неслабую ссылку.
Управление версиями символов также может играть роль.
Почти во всех случаях программы динамически связаны с libc.
Вы можете увидеть порядок загрузки библиотек с помощью ldd:
$ ldd simple_pthread
linux-vdso.so.1 => (0x00007fffaddff000)
libpthread.so.0 => /lib64/libpthread.so.0 (0x00007fa13a474000)
libc.so.6 => /lib64/libc.so.6 (0x00007fa13a0e0000)
/lib64/ld-linux-x86-64.so.2 (0x00007fa13a6a0000)
Здесь вы можете видеть, что libpthread находится перед libc в порядке компоновки. Это почти всегда будет так; libc всегда связан последним с использованием параметров компилятора по умолчанию.
Таким образом, программа, которая связана с libpthread, будет использовать версии этих символов pthread, поскольку они встречаются первыми в порядке связывания.
Если вы все еще не уверены, запуск вашей программы с переменной окружения LD_DEBUG, установленной в 'bindings', покажет фактические привязки символов, которые происходят.
Если вы используете статические ссылки, вы будете ссылаться на libc.a вместо libc.so. Вы можете использовать 'nm', чтобы просмотреть детали символа. Слабые символы имеют "W" или "W" для своего типа.
(Благодарим @Kaz за указание, что слабые символы не влияют на динамическое связывание).