Достоинства этого ответа будут зависеть от того, почему вы используете статические библиотеки. Если это позволит компоновщику отбросить неиспользуемые объекты позже, мне нечего добавить. Если это делается с целью организации - минимизации количества объектов, которые необходимо передать для связи приложений, - это расширение ответа «Занятый русский» может оказаться полезным.
Во время компиляции видимость всех символов в единице компиляции может быть установлена с помощью:
-fvisibility=hidden
-fvisibility=default
Это означает, что можно скомпилировать один файл "interface.c" с видимостью по умолчанию и большее количество файлов реализации со скрытой видимостью, без указания источника. Перемещаемая ссылка затем создаст один объектный файл, в котором не-API-функции «скрыты»:
ld -r interface.o implementation0.o implementation1.o -o relocatable.o
Объединенный объектный файл теперь может быть подвергнут объекту:
objcopy --localize-hidden relocatable.o mylibrary.o
Таким образом, у нас есть один объектный файл "библиотека" или "модуль", который предоставляет только предполагаемый API.
Вышеприведенная стратегия умеренно хорошо взаимодействует с оптимизацией времени соединения. Скомпилируйте с -flto и выполните перемещаемую ссылку, передав компилятору -r через компилятор:
gcc -fuse-linker-plugin -flto -nostdlib -Wl,-r {objects} -o relocatable.o
Используйте objcopy для локализации скрытых символов, как и раньше, затем вызовите компоновщик в последний раз, чтобы убрать локальные символы и любой другой мертвый код, который он может найти в объекте post-lto. К сожалению, relocatable.o вряд ли сохранил какую-либо информацию, связанную с этим:
gcc -nostdlib -Wl,-r,--discard-all relocatable.o mylibrary.o
Текущие реализации lto, по-видимому, активны на этапе перемещения. При включенном значении скрытые => локальные символы были удалены последней перемещаемой ссылкой. Без lto скрытые => локальные символы сохранились до последней перемещаемой ссылки.
Будущие реализации lto, вероятно, сохранят требуемые метаданные на этапе перемещения ссылки, но в настоящее время результатом перемещения ссылки является обычный старый объектный файл.