Заставьте ld выбирать корректную библиотеку

Существует два отличных подхода к этому.

  1. Любое резервное копирование и восстановление вся установка на другой машине.
  2. Совместно используйте .deb пакеты между машинами.

Преимущества для клонирующегося (опция № 1) включают только необходимость реализовать конфигурацию однажды. Недостатки включают копирование загрузчика/MBR для различных полных дисков, может быть хитрым. Кроме того, существует множество детализации статей, как сделать тот использующие различные утилиты.

Я вместо этого детализирую опцию № 2.

Linux Mint (и Ubuntu на данный момент...) является производными Debian (технически, non-LMDE выпуск Монетного двора основан на Ubuntu). Точка, формат пакета является архивом .deb, и диспетчер пакетов склонен - добираются (или GUI сверху его как "Центр программного обеспечения")

Просто необходимо прервать .deb пакеты, сохраненные в /var/cache/apt/archives/.

Если:

  1. Вы не используете apt-get clean удалить кэшируемые пакеты
  2. Обе машины выполняют тот же дистрибутив (и версия)
  3. Вы не смешиваете и соответствуете архитектуре

Это должно работать вполне приятно. Вы могли настроить rsync и пакеты акций оба пути по LAN также.

3
19.06.2014, 01:22
2 ответа

Есть три вещи, о которых вам нужно позаботиться при компиляции/сшивке с пакетом, не являющимся пакетом по умолчанию:

  • заголовки (обычно CFLAGS)
  • путь библиотеки времени компиляции (обычно LDFLAGS)
  • путь библиотеки времени исполнения (rpath через LDFLAGS, LD_RUN_PATH, LD_LIBRARY_PATH или ld. so.conf)

Вы не сказали, что такое prog, так что я не могу сказать, насколько хорошо может быть ее конфигурация (или если она использует autoconf? ), я видел много таких, которые надежно выполняют только первые два шага.

На этапе компоновки порядок путей к библиотеке актуален, предполагая, что вы используете инструментарий GNU (gcc & binutils), вы, вероятно, можете увидеть, что происходит, установив CFLAGS до configure (или, возможно, непосредственно в Makefile):

export CFLAGS="-Wl,-t"

Это передает опцию трассировки -t компоновщику. Может потребоваться добавить V=1 или VERBOSE=1 к команде make, если во время выполнения команды make выводятся только строки "CC" и "LD".)

Во время выполнения команды можно увидеть, что пытается ld.so, аккуратно установив LD_DEBUG, e. g.

LD_DEBUG=libs ./myprog

(или попробуйте значения files или symbols более подробно)

Чтобы правильно указать все три параметра во время сборки, вы должны уметь:

  • экспортировать CFLAGS="-I/usr/local/ssl-1. 0.2/include"
  • export LDFLAGS="-L/usr/local/ssl-1.0.2/lib -R/usr/local/ssl-1.0.2/lib"

затем переконфигурировать/перекомпилировать.

Вы используете --openssldir, а не более обычный --prefix (я рекомендую последний, а также использую make install_sw, если вам не нужны 1000 или около того man-страниц и симлинков, которые дает установка по умолчанию). Это может быть частью проблемы. По некоторым причинам библиотеки .so, которые вы показываете, известны в ld.so, не имеют суффикса версии (например, .so.1 .0.2), соответствующий "make install" должен был установить это для вас (через link-shared target в главном Makefile).

Опция -R инструктирует компоновщика встроить RPATH в исполняемый выход для конкретной библиотеки OpenSSL, чтобы ему не нужно было полагаться на умолчания, которые обычно предоставляет компоновщик (ld.so). Вместо этого вы можете модифицировать существующие двоичные файлы с помощью chrpath .

Это более или менее эквивалентно экспорту LD_LIBRARY_PATH=/usr/local/ssl-1.0.2/lib. Подробнее о RPATH и связанной с ней RUNPATH можно прочитать здесь: http://blog.tremily.us/posts/rpath/

В крайнем случае вы можете собрать OpenSSL без "shared" или с "noshared", это даст вам статические библиотеки, которые не будут иметь этой проблемы (но вполне могут иметь другие проблемы, например, для использования внутри ELF .so, вызывая проблемы PIC/PIE)


Основываясь на обновленных деталях, я считаю, что проблема в том, что 1.0.1 и 1.0.2beta устанавливают суффикс версии .so (SONAME) в 1.0.0. На первой системе с версией только 0.9.8 это не вызывает проблем; на второй системе с версиями 1.0.1 и 1.0.2, обе версии версий 1.0.0, это "первое совпадение выигрывает" на основе ld.so.{conf,d} заказа. Помните, ld компоновщик времени компиляции - это другая программа, отличная от ld.so компоновщика времени компиляции, и может иметь различное поведение (обычно приводящее к ошибкам в символах или, что еще хуже, как вы видели).

$ cd /usr/local/src/openssl/openssl/1.0.2beta1
$ readelf -a libssl.so | grep SONAME
0x0000000e (SONAME)                     Library soname: [libssl.so.1.0.0]

$ cat verchk.c
int main(int argc, char *argv[]) {
    printf("build: %s\n",OPENSSL_VERSION_TEXT);
    printf("run  : %s\n",SSLeay_version(SSLEAY_VERSION));
    return 0;
}

$ gcc -Wall  -I/usr/local/src/openssl/openssl-1.0.2-beta1/include \
    -Wl,-rpath /usr/local/src/openssl/openssl-1.0.2-beta1/ \
    -o verchk /usr/local/src/openssl/openssl-1.0.2-beta1/libcrypto.so verchk.c

$ ./verchk
build: OpenSSL 1.0.2-beta1 24 Feb 2014
run  : OpenSSL 1.0.2-beta1 24 Feb 2014

$ grep SHLIB_M...R= Makefile
SHLIB_MAJOR=1
SHLIB_MINOR=0.0

Обновление В OpenSSL-1.1 произошли некоторые изменения уровня API, приведенный выше код не скомпилируется с заголовками v1.1 и старыми библиотеками (неопределенная ссылка на `OpenSSL_version'').

SSLeay_version() теперь устарела и (в зависимости от OPENSSL_API_COMPAT) может быть #define-d к соответствующей функции API OpenSSL_version().

.
5
27.01.2020, 21:16

Путь к новой lib в одном из файлов в пределах /etc/ld.so.conf.d? Следующий запуск:-

#ldconfig -v

для восстановления кэша. Если вы быстро, то увидите новую lib в длинном списке, который она распечатывает (или подключите её к grep или less)

Может быть, путь уже был на первом сервере, но не на втором?

.
0
27.01.2020, 21:16

Теги

Похожие вопросы