Как статически связать библиотеку для создания общей библиотеки

Я пытаюсь создать общую библиотеку в Ubuntu Linux, которая зависит от libusb.

Я хочу статически связать libusb с моей общей библиотекой.

Итак, вы создали libusb как статическую библиотеку.

Теперь, когда я пытаюсь связать его с моей разделяемой библиотекой, компоновщик выдает ошибку, говоря, что я должен построить libusb, используя флаг -fPIC.

Справедливо.

Итак, я построил libusb с -fPIC, но затем я заметил, что размер .so стал значительно меньше, по-видимому, потому, что он больше не создавал статическую библиотеку.

Но я смог успешно собрать свою общую библиотеку с версией libusb -fPIC.

Но когда мое приложение пытается загрузить мою общую библиотеку, динамический загрузчик выдает следующую ошибку:

ошибка поиска символа: неопределенный символ: udev_new

Каким-то образом я хочу статически связать libusb с моей общей библиотекой, чтобы избежать подобных ошибок поиска символов, но я не могу найти правильную комбинацию параметров сборки gcc.

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

Спасибо.


person rohitsan    schedule 17.09.2018    source источник


Ответы (1)


Вероятно, проблема в том, что когда вы связываете библиотеку libusb.a, только символы в libusb, которые используются в вашей разделяемой библиотеке, связываются с вашим разделяемым объектом.

Чтобы обойти это, используйте флаг --whole-archive компоновщик. Вместо простого использования -lusb используйте

 -Wl,--whole-archive -lusb -Wl,--no-whole-archive
person nos    schedule 17.09.2018
comment
Я не использую -lusb. Я создал свой собственный файл .a из источника libusb, и я ссылаюсь на него в моем сценарии cmake. target_link_libraries (xxx libusb-1.0.a) - person rohitsan; 17.09.2018
comment
Затем вы можете запустить make VERBOSE=1, чтобы увидеть, какие команды выполняются. Если вместо -lusb на этапе компоновки команда просто указывает libusb-1.0.a (возможно, включая полный путь), вам нужно вместо этого заставить cmake испускать -Wl,--whole-archive libusb-1.0.a -Wl,--no-whole-archive - хотя я не знаю, как это сделать. - person nos; 17.09.2018
comment
Я заставил cmake испустить это, но все равно получаю ту же ошибку. Обратите внимание, что я не собирал libusb-1.0.a с -fPIC. - person rohitsan; 17.09.2018
comment
хорошо - я, вероятно, неправильно прочитал неопределенный символ, который у вас был, udev_new, который находится в библиотеке libudev, а не libusb, поэтому вам также нужно связать свое приложение с -ludev. Возможно, вам удастся также связать вашу общую библиотеку с -ludev, хотя новые цепочки инструментов могут проигнорировать это и вынудить вас использовать -ludev при связывании вашего приложения - по крайней мере, без дополнительных опций. - person nos; 17.09.2018
comment
Я не могу использовать -ludev, потому что хочу иметь возможность собирать двоичные файлы x64, x86 и arm64 с одной и той же машины сборки (с использованием разных компиляторов). Поэтому мне нужно собрать libusb со всем сгенерированным кодом в этой единственной статической библиотеке, чтобы я мог использовать ее для создания своей общей библиотеки. - person rohitsan; 17.09.2018
comment
ну, поскольку для libusb требуется libudev, вы либо связываете его с -ludev, что вы можете сделать как для arm64, так и для x64_86, если у вас есть библиотека libudev, созданная для соответствующей архитектуры, либо вы встраиваете libudev в свою общую библиотеку, как вы это делали с libusb - person nos; 17.09.2018
comment
Мне нужно собрать версию этого для arm64 на моем компьютере x86_64. Но мне очень трудно установить libudev-dev: arm64 на этот ящик, чтобы включить это. Вы можете помочь? - person rohitsan; 19.09.2018