组合静态库

发布于 2024-07-14 22:32:55 字数 450 浏览 4 评论 0原文

假设我有三个 C 静态库,例如 libColor.a ,它依赖于 *libRGB.*a ,而后者又依赖于 libPixel.a 。 据说库 libColor.a 依赖于库 libRGB.a,因为 libColor.a 中定义了一些符号libRGB.a。 如何将上述所有库组合到一个独立的新 libNewColor.a 中?

独立意味着新库应该定义所有符号。 因此,在链接时我只需要给出-lNewColor。 新库的大小应该最小,即它不应该包含 libRGB.a 中不被 libColor.a 等使用的任何符号。 我尝试使用 ar 命令中的各种选项(用于创建和更新静态库/档案)。

Suppose I have three C static libraries say libColor.a which depends on *libRGB.*a which in turn depends on libPixel.a . The library libColor.a is said to depend on library libRGB.a since there are some references in libColor.a to some of symbols defined in libRGB.a. How do I combine all the above libraries to a new libNewColor.a which is independent?

Independent means the new library should have all symbols defined. So while linking I just need to give -lNewColor. The size of the new library should be minimal i.e it should not contain any symbols in libRGB.a which is not used by libColor.a etc.
I tried my luck using various options in ar command (used to create and update static libraries/archives).

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

攒一口袋星星 2024-07-21 22:32:55

GNU 归档器的一个很少使用的功能是归档脚本,它是一个简单但功能强大的接口,并且它可以完全执行您想要的操作,例如,如果以下脚本称为 script.ar:

CREATE libNewColor.a
ADDLIB libColor.a
ADDLIB libRGB.a
ADDLIB libPixel.a
SAVE
END

那么您可以按如下方式调用 ar:

ar -M < script.ar

您将获得 libNewColor.a,其中包含 libColor.a、libRGB.a 和 libPixel.a 中的所有 .o 文件。

此外,您还可以使用 ADDMOD 命令添加常规 .o 文件:

CREATE libNewColor.a
ADDLIB libColor.a
ADDLIB libRGB.a
ADDLIB libPixel.a
ADDMOD someRandomCompiledFile.o
SAVE
END

此外,在 Makefile 中生成这些脚本非常容易,因此我通常创建一个通用的 makefile 规则来创建档案,该规则实际上生成脚本并在脚本。 像这样的事情:

$(OUTARC): $(OBJECTS)
    $(SILENT)echo "CREATE $@" > $(ODIR)/$(ARSCRIPT)
    $(SILENT)for a in $(ARCHIVES); do (echo "ADDLIB $a" >> $(ODIR)/$(ARSCRIPT)); done
    $(SILENT)echo "ADDMOD $(OBJECTS)" >> $(ODIR)/$(ARSCRIPT)
    $(SILENT)echo "SAVE" >> $(ODIR)/$(ARSCRIPT)
    $(SILENT)echo "END" >> $(ODIR)/$(ARSCRIPT)
    $(SILENT)$(AR) -M < $(ODIR)/$(ARSCRIPT)

虽然现在我看着它,我猜如果 $(OBJECTS) 为空(即,如果您只想合并档案而不添加额外的对象文件),它就不起作用,但我将把它作为练习如果需要,请读者修复该问题... :D

以下是此功能的文档:

https://sourceware.org/binutils/docs/binutils/ar-scripts.html#ar-scripts

A little used feature of the GNU archiver is the archive script, it is a simple but powerful interface, and it can do exactly what you want, for example if the following script is called script.ar:

CREATE libNewColor.a
ADDLIB libColor.a
ADDLIB libRGB.a
ADDLIB libPixel.a
SAVE
END

Then you could invoke ar as follows:

ar -M < script.ar

and you would get libNewColor.a that contains all of the .o files from libColor.a libRGB.a and libPixel.a.

Additionally you can also add regular .o files as well with the ADDMOD command:

CREATE libNewColor.a
ADDLIB libColor.a
ADDLIB libRGB.a
ADDLIB libPixel.a
ADDMOD someRandomCompiledFile.o
SAVE
END

Furthermore it is super easy to generate these scripts in Makefiles, so I typically create a somewhat generic makefile rule for creating archives which actually generates the script and invokes ar on the script. Something like this:

$(OUTARC): $(OBJECTS)
    $(SILENT)echo "CREATE $@" > $(ODIR)/$(ARSCRIPT)
    $(SILENT)for a in $(ARCHIVES); do (echo "ADDLIB $a" >> $(ODIR)/$(ARSCRIPT)); done
    $(SILENT)echo "ADDMOD $(OBJECTS)" >> $(ODIR)/$(ARSCRIPT)
    $(SILENT)echo "SAVE" >> $(ODIR)/$(ARSCRIPT)
    $(SILENT)echo "END" >> $(ODIR)/$(ARSCRIPT)
    $(SILENT)$(AR) -M < $(ODIR)/$(ARSCRIPT)

Though now that I look at it I guess it doesn't work if $(OBJECTS) is empty (i.e. if you just want to combine archives without adding extra object files) but I will leave it as an exercise for the reader to fix that issue if needed... :D

Here are the docs for this feature:

https://sourceware.org/binutils/docs/binutils/ar-scripts.html#ar-scripts

半窗疏影 2024-07-21 22:32:55

1/ 从每个库中提取所有目标文件(使用 ar),并尝试在没有库或任何目标文件的情况下编译代码。 您可能会得到大量未定义符号。 如果没有得到未定义的符号,请转到步骤 5。

2/ 获取第一个符号并找出哪个目标文件满足该符号(使用 nm)。

3/ 写下该目标文件,然后编译您的代码,包括新的目标文件。 您将获得未定义符号的新列表,或者,如果没有,请转到步骤 5。

4/ 转到步骤 2。

5/ 将列表中的所有目标文件(如果有)合并到单个库中(再次使用 <代码>ar)。

砰! 你有它。 尝试在不使用任何对象的情况下链接代码,但使用新库。

整个事情可以通过 shell 脚本相对轻松地实现自动化。

1/ Extract ALL of the object files from each library (using ar) and try to compile your code without the libraries or any of the object files. You'll probably get an absolute bucket-load of undefined symbols. If you get no undefined symbols, go to step 5.

2/ Grab the first one and find out which object file satisfies that symbol (using nm).

3/ Write down that object file then compile your code, including the new object file. You'll get a new list of undefined symbols or, if there's none, go to step 5.

4/ Go to step 2.

5/ Combine all the object files in your list (if any) into a single library (again with ar).

Bang! There you have it. Try to link your code without any of the objects but with the new library.

This whole thing could be relatively easily automated with a shell script.

椵侞 2024-07-21 22:32:55

静态库只不过是一些目标文件 (.o) 的存档。 您可以做的是提取两个库中的所有对象(使用“ar x”),然后使用“ar”将它们链接到一个新库中。

A static library is not much more than an archive of some object files (.o). What you can do is extract all the objects in the two libraries (using "ar x") and then use "ar" to link them together in a new library.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文