)
c-ares 从源码编译安装全指南AutoTools、CMake 与跨平台构建实战基于 MongoDB 仓库 vendored 的 c-ares 1.27.0【免费下载链接】mongoThe MongoDB Database项目地址: https://gitcode.com/GitHub_Trending/mo/mongoc-ares 是一个以异步方式执行 DNS 解析与查询的 C 语言库其核心价值在于非阻塞应用可以在等待域名解析结果的同时继续处理其他 I/O。本文以当前 MongoDB 仓库中 vendored 的 c-ares 源码 为主线系统讲解从源码编译、安装 c-ares 的全部官方路径——AutoTools、CMake、各类跨平台特殊场景——并在此基础上深入剖析该仓库将 c-ares 集成进自身构建体系Bazel的真实做法。读完本文你将能够独立完成 c-ares 在 Unix、Windows、Android、QNX 等平台上的源码构建与安装也能看懂大型 C 项目如何收编第三方 C 库。1. 先弄清楚二进制包安装与源码编译的区别INSTALL.md 开篇就划清了一条边界很多人会直接下载 c-ares 的二进制发行包binary distribution但本文档不讨论二进制包如何安装只讨论如何从源代码完成编译、构建与安装compile、build、install。原因也很直观二进制包面向普通使用者而源码编译面向需要定制构建选项、需要交叉编译、或者需要将库嵌入自有构建体系的开发者。在深入编译流程之前先明确本仓库中 c-ares 的存在形态这对理解后面所有命令都很有帮助源码本体位于 src/third_party/cares/dist/包含完整的configure、configure.ac、Makefile.in体系、src/目录下的全部库源码以及include/公共头文件仓库针对 Linux 各 CPU 架构预先生成并提交了构建产物头文件见 src/third_party/cares/platform/ 下的linux_x86_64、linux_aarch64、linux_ppc64le、linux_s390x四套目录仓库并非使用 INSTALL.md 中的make install流程把 c-ares 装进系统而是通过 BUILD.bazel 将其编译为静态库目标//src/third_party/cares:ares详见第 10 节。2. 从 Git 仓库构建buildconf 与 GIT-INFO如果你拿到的是 Git 仓库中的代码而非官方 release tarball构建前需要多走一步生成构建文件的工序具体指引记录在仓库根目录的 GIT-INFO 文件中。其要点如下Unix 平台需要先运行./buildconf仓库源码中确实存在 buildconf 脚本生成新鲜的configure脚本前提是本地已安装 Autotoolsautoconf/automake/libtool 等。Windows 平台对应运行buildconf.bat仓库中同样存在 buildconf.bat。使用 CMake 时则无需上述步骤无论代码来自 Git 还是官方 release tarballCMake 的构建步骤完全一致。关于 GIT-INFO 文件本身仓库中的 GIT-INFO 内容说明了它的身份它只存在于 Git 检出中从不进入 release 归档其作用是作为buildconf.bat中的哨兵sentinel文件用以区分Git 检出与release / 每日快照归档。在 *nix 类系统上先运行./buildconf生成新鲜的 configure 脚本这需要本地安装 autotools。值得注意的是本仓库的 scripts/import.sh 正是从 Git 导入 c-ares这一流程的实际落地它从cares-1_27_0分支克隆源码后第一件事就是运行autoreconf -fi等价于手动执行 buildconf 体系随后才进入 configure/make 阶段。这也印证了Git 检出必须先生成构建文件这一规则在真实工程中的执行方式。3. AutoTools 构建标准 Unix 三/四步走3.1 基本流程对于绝大多数 Unix 平台Linux、FreeBSD 等解压源码归档后一次标准的安装只需三到四步./configure make make install最后一步make install通常需要 root 权限除非安装目录对当前用户可写。如果是从 Git 检出源码请先阅读 GIT-INFO 中关于 buildconf 的说明见第 2 节。3.2 查看全部配置选项想要获得 configure 的全部可用选项执行./configure --help这会列出所有可开关的功能项、安装路径变量与编译选项是了解该版本 c-ares 支持哪些特性的第一手资料。3.3 自定义安装前缀如果不想把 c-ares 装到默认的/usr/local目录树必须在运行 configure 时就指定安装前缀./configure --prefix/path/to/c-ares/tree如果你对该目录拥有写权限就可以在非 root 身份下直接make install。一个典型场景是把 c-ares 安装到自己的主目录做一次本地安装./configure --prefix$HOME make make install3.4 更多常用选项INSTALL.md 针对编译器的选择与库形态给出了几个高频选项强制使用标准 cc 编译器当系统同时存在 cc 与 gcc 时CCcc ./configure # 等价写法 env CCcc ./configure仅编译静态库禁用共享库./configure --disable-shared开启调试选项针对 c-ares 开发者且使用 gcc 的场景./configure --enable-debug3.5 特殊编译器与 libc 的特殊情形uClibc某些版本的 uClibc 需要以CPPFLAGS-D_GNU_SOURCE1配置才能获得正确的 large file support大文件支持。Linux 上的 Open Watcom C 编译器需要为 configure 显式提供一组工具链变量./configure CCowcc AR$WATCOM/binl/wlib AR_FLAGS-q \ RANLIB/bin/true STRIP$WATCOM/binl/wstrip CFLAGS-Wextra4. 交叉编译Cross Compile交叉编译是嵌入式、移动端开发的刚需。INSTALL.md 给出的完整方法论是下载解包 → 设置交叉工具链环境变量 → 携带--host/--build运行 configure → make → make install。以下脚本是官方文档给出的完整示例目标平台为 IBM 405GP PowerPC 处理器工具链来自 MonteVista 的 Hardhat Linux#! /bin/sh export PATH$PATH:/opt/hardhat/devkit/ppc/405/bin export CPPFLAGS-I/opt/hardhat/devkit/ppc/405/target/usr/include export ARppc_405-ar export ASppc_405-as export LDppc_405-ld export RANLIBppc_405-ranlib export CCppc_405-gcc export NMppc_405-nm ./configure --targetpowerpc-hardhat-linux \ --hostpowerpc-hardhat-linux \ --buildi586-pc-linux-gnu \ --prefix/opt/hardhat/devkit/ppc/405/target/usr/local \ --exec-prefix/usr/local其中--host指定目标运行平台--build指定构建机平台二者必须同时给出--target在交叉编译场景下通常与--host一致--prefix决定 c-ares 的安装位置交叉编译时 configure 往往无法自动探测目标系统是否具备随机数生成设备因此可能需要额外提供类似--with-random/dev/urandom的参数。如果 configure 顺利通过之后照常执行make与make install即可。在部分场景下上面的长串命令可以简化为./configure --hostARCH-OS5. 特殊平台构建要点5.1 CygwinWindowsCygwin 下的安装与 Unix 几乎一致在 c-ares 根目录用sh configure运行 configure 脚本。务必确保sh可执行文件位于/bin/否则 configure 会在接近结束时失败。之后运行make。5.2 QNXQNX 面向资源受限环境其头文件设置了保守的限制其中就包括FD_SETSIZE宏——默认值为 32。c-ares 库返回的套接字描述符可能超过该值当它们被传入使用fd_set宏的select(..)调用时会引发内存错误memory faults / SIGSEGV 崩溃。官方推荐的通用解决方案是在 configure 时覆盖CFLAGS# configure CFLAGS-DFD_SETSIZE64 -g -O2将FD_SETSIZE提升到 64 即可规避描述符越界导致的崩溃。5.3 RISC OS该库可使用 gccsdk 交叉编译CCriscos-gcc ARriscos-ar RANLIBriscos-ar -s ./configure \ --hostarm-riscos-aof --without-random --disable-shared make其中riscos-gcc与riscos-ar是指向 gccsdk 工具的链接。构建完成后可将你的程序与c-ares/lib/.libs/libcares.a链接。5.4 Android官方文档给出的方式是configure 交叉编译法已在 Android NDK r7b 上验证先将 Android NDK 的工具链准备为 standalone 形式调用脚本./tools/make-standalone-toolchain.sh这会生成一套常规的交叉编译工具链。假设将其放在/opt下则可这样配置export PATH/opt/arm-linux-androideabi-4.4.3/bin:$PATH ./configure --hostarm-linux-androideabi [more configure options] make如果直接从 Git 仓库编译老版本 automake 可能报出如下错误checking host system type... Invalid configuration arm-linux-androideabi: system androideabi not recognized configure: error: /bin/sh ./config.sub arm-linux-androideabi failed该问题的根源是config.sub/config.guess过旧、不认识androideabi这个系统标识。解决办法是获取更新版本的config.sub与config.guess可取自 GNU config 项目替换系统自带的旧版本。系统自带的版本通常位于 automake 目录中可用find /usr -name config.sub定位。6. CMake 构建跨平台现代方案当前版本的 c-ares 引入了基于 CMake v3 的构建系统已在包括 Windows、Linux、FreeBSD、macOS、AIX 与 Solaris 在内的大多数平台上得到验证。最基础形式的 CMake 构建如下cd /path/to/cmake/source mkdir build cd build cmake -DCMAKE_BUILD_TYPERelease -DCMAKE_INSTALL_PREFIX/usr/local/cares .. make sudo make install6.1 CMake 选项总表CMake 选项通过命令行以-D${OPTION}${VALUE}形式传入取值均为布尔类型可填On、Off、True、False。INSTALL.md 给出的完整选项表如下Option NameDescriptionDefault ValueCARES_STATICBuild the static libraryOffCARES_SHAREDBuild the shared libraryOnCARES_INSTALLHook in installation, useful to disable if chain buildingOnCARES_STATIC_PICBuild the static library as position-independentOffCARES_BUILD_TESTSBuild and run testsOffCARES_BUILD_CONTAINER_TESTSBuild and run container tests (implies CARES_BUILD_TESTS, Linux only)OffCARES_BUILD_TOOLSBuild toolsOnCARES_SYMBOL_HIDINGHide private symbols in shared librariesOffCARES_THREADSBuild with thread-safety supportOn几个选项的实战含义值得展开CARES_STATIC与CARES_SHARED分别控制静态库与共享库的产出二者默认分别为 Off 与 On——即默认只产出共享库需要静态库时显式加-DCARES_STATICOnCARES_STATIC_PIC用于将静态库编译为位置无关代码PIC当静态库需要被链接进共享库/插件时应当开启CARES_INSTALL在链式构建chain building即把 c-ares 作为更大构建流程中的一环时建议关闭避免安装步骤干扰外层流程CARES_BUILD_CONTAINER_TESTS隐含依赖CARES_BUILD_TESTS且仅限 LinuxCARES_SYMBOL_HIDING开启后会在共享库中隐藏私有符号缩小动态符号表CARES_THREADS默认开启提供线程安全支持。6.2 使用 Ninja 生成器Ninja 是面向 CMake 这类生成器的下一代构建系统特点是高度并行化构建。其用法与普通构建几乎一致仅需在生成阶段指定 Ninjacd /path/to/cmake/source mkdir build cd build cmake -DCMAKE_BUILD_TYPERelease -DCMAKE_INSTALL_PREFIX/usr/local/cares -G Ninja .. ninja sudo ninja install6.3 Windows MSVC 命令行NMakecd \path\to\cmake\source mkdir build cd build cmake -DCMAKE_BUILD_TYPERelease -DCMAKE_INSTALL_PREFIXC:\cares -G NMake Makefiles .. nmake nmake install6.4 Windows MinGW-w64 命令行经 MSYScd \path\to\cmake\source mkdir build cd build cmake -DCMAKE_BUILD_TYPERelease -DCMAKE_INSTALL_PREFIXC:\cares -G MSYS Makefiles .. make make install7. 平台专属构建体系Win32 专题7.1 DLL 与 CRT 链接问题必读INSTALL.md 在这里给出了 Windows 开发者必须遵守的铁律构建 DLL 时使用静态 CRT 链接是高度不推荐的做法在同一应用内混用多种 CRT是应当不惜一切代价避免的行为。官方文档强烈建议每个 Windows 开发者通读并理解 Microsoft Learn 上关于《Use the C Run-Time》的文章尤其是当你决定不遵循上述建议时更需完全理解其后果。排查技巧如果你的应用出现奇怪的行为或内存损坏memory corruption在求助之前请先尝试用debug multithreaded dynamic C runtime调试版多线程动态 C 运行时重新编译应用所依赖的每一个库以及应用本身。7.2 MinGW32确保 MinGW32 的 bin 目录在搜索路径中set PATHc:\mingw32\bin;%PATH%然后在根目录运行make -f Makefile.m32。7.3 MSVC 6 注意事项若使用 MSVC 6官方要求使用 2003 年 2 月版的 PSDKPlatform SDK。7.4 MSVC 命令行构建先从命令行运行vcvars32.bat以获取正确的编译环境。该文件是微软开发环境的一部分若按默认目录安装 Visual C/C 6其位置在C:\Program Files\Microsoft Visual Studio\vc98\bin。更详细的说明见仓库中的 README.msvc。7.5 静态链接 c-ares 的重要说明当你的应用使用静态c-ares 库时必须在 CFLAGS 中加入-DCARES_STATICLIB。否则链接器会去查找动态导入符号dynamic import symbols导致链接失败。8. OS/2 与 NetWare 构建8.1 IBM OS/2OS/2 下的构建与 Unix 差异不大需要准备emx 0.9d、GNU make、GNU patch、ksh、GNU bison、GNU file utilities、GNU sed、autoconf 2.13。两个常见问题链接时若报_errno为未定义符号从 text segment 引用需要在定义中加入-D__ST_MT_ERRNO__若生成的可执行文件体积异常巨大多半是 makefile 的CFLAGS中带有-g。8.2 NetWare编译libcares.a/libcares.lib需要任意 gcc/nlmconv 或 CodeWarrior 7 PDK 4 及以上版本构建平台上可运行的 GNU make 与 awk以及 Novell 的 LibC SDK 或 CLib SDK。操作步骤将编译器、链接器和工具加入搜索路径在 Linux 上确保变量OSTYPE包含字符串linux将变量NDKBASE指向 Novell NDK 的基目录然后在源码顶层目录执行make -f Makefile.netware。9. vcpkg、WATCOM 与移植平台清单9.1 通过 vcpkg 依赖管理器安装vcpkg 是微软维护的 C/C 依赖管理器其 c-ares port 由微软团队成员与社区贡献者持续维护。使用步骤git clone vcpkg 官方仓库 cd vcpkg ./bootstrap-vcpkg.sh ./vcpkg integrate install ./vcpkg install c-ares若发现 vcpkg 中的 c-ares 版本过旧可以在 vcpkg 仓库上提交 issue 或 pull request。9.2 OpenWatcom 构建使用 OpenWatcom 构建 c-ares 至少需要 1.9 版本安装与当前宿主机平台匹配的版本。安装完成后打开新的命令提示符并执行cd \path\to\cmake\source buildconf.bat wmake -u -f Makefile.Watcomwmake完成后应能得到adig.exe、ahost.exe以及静态与动态两个版本的 libcares。9.3 已确认可移植平台清单PORTS以下是一份可能不完整的、c-ares 已被成功编译过的硬件与操作系统清单Alpha Tru64 v5.0 5.1ARM Android 1.5, 2.1, 2.3MIPS IRIX 6.2, 6.5Power AIX 3.2.5, 4.2, 4.3.1, 4.3.2, 5.1, 5.2i386 Linux 1.3, 2.0, 2.2, 2.3, 2.4, 2.6i386 Novell NetWarei386 Windows 95, 98, ME, NT, 2000, XP, 2003x86_64 Linux10. 仓库实战MongoDB 如何将 c-ares 集成进 Bazel 构建INSTALL.md 描述的是面向独立发行/系统安装的构建流程而本仓库则展示了另一种工业级做法——把 c-ares 作为 vendored 第三方库编入自身构建系统。从源码结构看仓库采取的是预构建头文件 Bazel 静态库目标的组合策略10.1 平台相关头文件预生成src/third_party/cares/platform/ 下为每种支持的 Linux CPU 架构linux_x86_64、linux_aarch64、linux_ppc64le、linux_s390x各保存了一份install/include目录内含ares.h、ares_build.h、ares_dns.h、ares_dns_record.h、ares_nameser.h、ares_rules.h、ares_version.h等公共头文件。这相当于把configure make install产出的、随架构而变的生成头文件固化进了版本库从而让 Bazel 构建无需在每次编译时重新运行 autotools。10.2 Bazel 目标定义BUILD.bazel 定义了一个名为ares的cc_library目标srcs列出 dist/src/lib/ 下全部库源码包括ares_init.c、ares_getaddrinfo.c、ares_query.c、ares_search.c、ares_parse_*_reply.c系列解析函数、ares_event_*.c事件驱动实现等hdrs与includes通过select()按 CPU 架构aarch64/x86_64/s390x/ppc64le分别引用platform/arch/build/include与platform/arch/install/include即第 10.1 节预生成的头文件local_defines注入了HAVE_CONFIG_H1对应 autotools 生成的ares_config.h机制、CARES_BUILDING_LIBRARY构建库本体而非使用方、c_ares_EXPORTS并在 macOS 上额外注入_DARWIN_C_SOURCE通过target_compatible_with将非 Linux 平台标记为不兼容即该 Bazel 目标仅面向 Linux同目录下的 MODULE.bazel 将其声明为名为c-ares的 Bazel 模块依赖rules_cc、bazel_skylib与platforms。这些 define 与选项设计恰好呼应了 INSTALL.md 中的若干要点CARES_BUILDING_LIBRARY是典型的构建库自身宏对应静态/共享库构建场景中的符号导出控制而HAVE_CONFIG_H1正是 autotools 配置体系在源码中的化身。10.3 导入与再生成流程scripts/import.sh 完整记录了从上游 Git 导入新版本 c-ares的自动化流程可作为任何团队升级 vendored 第三方库的参考模板从cares-1_27_0分支克隆源码到dist/当前仓库对应 c-ares 1.27.0运行autoreconf -fi生成构建文件与第 2 节 buildconf 流程对应在宿主机对应的platform/host_os_host_arch/build_tmp中执行configure指定--prefix与 mongodbtoolchain 的 gcc/g随后make install将生成的ares_config.h构建期配置头文件复制到build/include将ares.h、ares_build.h、ares_dns.h等公共头文件复制到install/include清理build_tmp、install_tmp与各类缓存、测试、文档等冗余内容仅保留库源码与两个头文件目录。由此可见INSTALL.md 中描述的 AutoTools 流程不仅适用于独立安装 c-ares也被本仓库直接用作第三方依赖的导入流水线——configure/make 在这里充当了头文件生成器的角色最终交付给 Bazel 的则是纯净的源码树加预生成头文件。结语c-ares 的构建体系看似庞杂实则脉络清晰官方主推 AutoToolsUnix与 CMake跨平台两条主线其余平台QNX、RISC OS、Android、OS/2、NetWare、Watcom、vcpkg均为特化分支。无论你走哪条路核心动作都是配置configure→ 编译make/ninja/nmake→ 安装install三步。而在大型项目中正如本仓库所示这些流程往往被封装进 Bazel 之类的构建系统与导入脚本之中——理解 INSTALL.md 的全部细节正是读懂这类集成的起点。【免费下载链接】mongoThe MongoDB Database项目地址: https://gitcode.com/GitHub_Trending/mo/mongo创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考