gpt4 book ai didi

c++ - 用于库编译的C/C++约定/工具链

转载 作者:塔克拉玛干 更新时间:2023-11-03 06:55:28 29 4
gpt4 key购买 nike

我C / C++的基本问题在于库编译 Realm 。 例如软件A使用库Z,因此您必须先编译库Z,然后才能编译并随后使用和/或开发软件A。

在许多情况下,都存在配置项目然后调用make + make install的想法。例如。您打开命令行并输入:

./configure
make
make install
./configure是一个shell脚本,位于项目的顶级目录中。我想它会检查系统上是否存在所有依赖项,并保存这些依赖项的路径。以后,make可以利用这些收集的信息为编译器提供相应的包含路径和库位置(例如.so / .a文件的位置)。
make负责以正确的顺序编译和链接源文件(由makefile指定,该文件由I-dont-know生成,格式为XYZ)。当然,它本身并不编译/链接任何东西,而是调用实际的编译器和链接器来完成其工作。
make install接收生成的二进制文件并将其放置在系统中的某个位置(例如,如果项目是库,则为/ usr / lib;对于可执行文件为/ usr / bin)。如果手头的项目是一个库,则据说它也将使用该库的头文件并将它们安装在系统中的某个位置。

这是一个相对复杂的过程。让我们使用CMI来表示这种类型的编译过程(CMI = configure-make-install)。而且,据我所知,CMI概念是特定于Linux世界的。例如,在Windows上它无法正常工作因为没有可用于执行./configure的 shell 。 make甚至可能仅限于gcc / g++,但我不知道是否是这种情况。

最重要的是,我什至不知道在哪里查找。我还想了解CMI概念是否支持同时安装不同版本的库。假设您是软件B和软件C的开发者。软件B和C都依赖于库Y,但是无论出于何种原因,B都需要Y 1.0.x,而C需要1.1.x。如果make install将库的头文件放在系统上的某个地方,会不会发生冲突?再次,我问自己,我可以在哪里查找?

让我们讨论一个示例库: libzip。主页未说明支持或推荐使用哪些编译器或平台。您现在将如何进行?

有趣的是,该页面声称MySQL Workbench正在使用libzip。 Windows还提供了MySQL Workbench,因此我想libzip可以在Windows上编译。

我还观察到libzip附带了 CMakeLists.txt configure 脚本。在 CMake模板中甚至还有一个 libzip.pc。,据说是 pkg-config 工具。还有Makefile.am(无论是什么)和Makefile.in,据说是另一个CMake模板。最后但并非最不重要的一点是,我注意到一个文件夹m4和.m4文件(在m4文件夹内和项目的根文件夹中)。但是,请不要忘记cmake-config.h.in,cmake-zipconf.h.in。

因此,如果要编译libzip,则必须考虑以下替代方法:
  • 使用CMI概念
  • 在Windows上不适用(对吗?)
  • 使用CMake,这是各种meta构建系统
  • ,那么您必须决定应为gcc生成哪种编译器/ IDE CMake。 MSVC? Mingw还是QTSDK / MingW? (无论有什么不同)
  • 可能会使用M4,无论
  • 是什么

    M4似乎与GNU autoconf有关。我想我也可以添加到上面的列表中。

    (旁注:到目前为止,我已经尝试使用CMake + Visual Studio 2010的组合来编译libzip。目前,我正在修复各种编译错误。)

    这是我的主要观察结果:

    libzip是一个简单的库;只是一些 zipper 的东西。但是,编译涉及许多工具,即使对于高级程序员而言,这也是一项艰巨的任务。

    而且,缺少大多数这些工具的文档(否则为什么我会有所有这些问题,却不知道在哪里找到答案?)。更不用说大多数工具甚至不花大量时间进行逆向工程来修复(例如,令人叹为观止的CMake FindPackage脚本)就无法工作。

    我可以像这样继续WEEKS。我迷失于众多的编译概念,它们之间如何相互联系,它们可以很好地使用哪些平台和编译器等。

    另一个示例:RetroShare。即使是Windows is documented的编译过程,也很难完成编译。只需考虑在Windows上编译RetroShare涉及QtSDK / MingW,Cygwin和MingW / MSYS,它们全部用于不同的部件/依赖项。这些工具如何协同工作?

    我完全迷失了,我想告诉我如何考虑所有这些工具/工具链/编译器/平台,如何处理此类问题以及如何保护自己的思想免受严重损害。

    你们是不是非常聪明?还是我非常愚蠢?为什么这么复杂(或不是)?

    最佳答案

    "I could go on like that for WEEKS."



    您听起来有些困惑。我将解决一些具体问题。

    “configure-make-install”过程特别使用了 make,它是一个更通用的工具。即,make和makefile可以以其他方式使用。记在脑子里。

    "make is responsible for compiling and linking the source files in the correct order (as specified by makefiles, which are generated by I-dont-know and have format XYZ)."



    迟早,您几乎肯定会不得不学习自己编写makefile。 Make是一个构建系统,对于C / C++程序员而言,这是一个非常有用的,几乎是必需的工具。如果使用IDE,则它可能已经在为您创建makefile。这是一个为小型项目手工编写的示例makefile:
    wx = `wx-config --cxxflags --libs`

    test1: main.cpp main.h window.o
    g++ -Wall -g main.cpp window.o -o test1 $(wx)

    window.o: window.cpp window.h
    g++ -Wall -g -c window.cpp -o window.o $(wx)

    第一行定义一个变量,链接器的一些标志,此后使用两次。如果在命令行上使用gcc,那么接下来的两位应该很熟悉。要在不使用 make的情况下构建该项目,您将首先通过 g++ ...然后是 test1来编译window.o。有了makefile之后,您要做的就是运行 make。将更多的对象(.o)文件添加到项目中,它开始显得非常方便。另外,您可以将不同的“ 目标”写入一个makefile。周围有各种make教程,以及GNU版本的官方文档:

    http://www.gnu.org/software/make/manual/make.html

    不难发现。

    "make install takes the resulting binary files and places them somewhere in the system"


    make install目标,通常被定义为在configure-make-install上下文中使用的makefile中执行此操作。您可以在上面的makefile中添加这样的东西:
    install: test1
    cp test1 /usr/local/bin/

    冒号之后与目标位于同一行的任何内容都是先决条件-它引用必须在构建树中存在的文件(或必须运行的另一个目标指令)。如果该文件不存在(或者自创建以来其某些先决条件已更改),并且存在一个具有相同名称的目标(在这种情况下为 test1,请查看之前的先决条件),则该目标伪指令为首先运行。

    "Also, the CMI concept is - as far as I can tell - specific for the Linux world."



    不,但是它与Windows世界有些不同。有时相对于 autotools 而言,它可以用来生成配置脚本和相应的makefile。请注意,如果您安装了 mingw ,则可以在Windows上使用CMI软件包。

    "use CMake, which is a meta build system of sorts"



    CMake本质上与make相同,只是有所不同。 make仅在makefile中显式调用gcc时才使用。可以编写makefile来执行shell脚本可以做的几乎所有事情,包括运行编译器等。CMake希望变得更加可移植/平台化,甚至对用户友好。有些人喜欢它。

    "If make install places the library's header files somewhere on the system, won't there be collisions?"



    理想情况下,不会。自动工具(“CMI”)设置的部分要点是允许打包程序实现机制来解决此类问题(如果存在)。您可以安装同一库的多个版本。 WRT header (如果更改了),它们(希望)保持向后兼容,就像库本身一样。如果不是,应该对此有一些明确的指示(“版本2与版本1不兼容!”),当发生这种情况时,任何有头脑的人将从一开始就具有版本2的不同 header ,并在API中进行引用。

    关于c++ - 用于库编译的C/C++约定/工具链,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10471441/

    29 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com