使用 rpmbuild构建带条件宏的 RPM 包:依赖安装与调试指南

在使用 rpmbuild 构建 RPM 软件包时,某些构建依赖可能通过 条件宏(conditional macros) 控制。例如,只有在启用 --with mpich 选项时,才需要安装 mpich-devel。若未正确处理这些条件依赖,构建过程会因缺少依赖而失败。

本文档将指导你:

  1. 识别 spec 文件中的条件宏
  2. 理解 --with / --without 与宏的关系
  3. 正确安装由条件宏触发的构建依赖
  4. 调试和验证宏展开结果

一、什么是条件宏?

RPM spec 文件支持通过 %if %{with xxx}%if %{without xxx} 等语法实现条件逻辑。常见的用法包括:

%if %{with mpich}
BuildRequires: mpich-devel
%endif

%if %{without cuda}
# 排除 CUDA 相关代码
%endif

这些条件是否生效,取决于构建时是否通过 rpmbuild --with xxx--without xxx 启用对应宏。

📌 注意:rpmbuild --with feature 等价于在内部定义 %{?with_feature} 宏为 1


二、如何查看 spec 文件中包含哪些条件宏?

方法 1:直接阅读 spec 文件

搜索以下关键词:

grep -E '%\{with_|%\{without_|%if.*with|%if.*without' your-package.spec

示例输出:

%if %{with mpich}
%if %{without openmpi}

这表示该 spec 支持 --with mpich--without openmpi 两个构建选项。

方法 2:列出所有可用的构建选项(推荐)

RPM spec 文件通常会在开头通过 %global 或注释说明支持的选项:

# Build with MPICH support: rpmbuild --with mpich ...
# Build without CUDA: rpmbuild --without cuda ...

也可以使用以下命令提取所有可能的 with_/without_ 宏:

sed -n 's/.*%{\(with_\|without_\)\([^}]*\)}.*/\1\2/p' your-package.spec | sort -u

三、如何安装由条件宏触发的构建依赖?

当你运行如下命令时:

rpmbuild -ba --with mpich your-package.spec

如果报错:

error: Failed build dependencies:
    mpich-devel is needed by your-package.x86_64

说明你需要安装 mpich-devel。以下是两种推荐方法:


✅ 方法 A:使用 dnf builddep 自动安装(推荐)

dnf builddep 可以自动解析 spec 文件并安装所有 BuildRequires包括由条件宏启用的依赖,但需显式传递宏定义。

# 安装必要工具
sudo dnf install rpm-build dnf-plugins-core

# 安装依赖(注意:--with mpich 对应 --define 'with_mpich 1')
sudo dnf builddep --define 'with_mpich 1' your-package.spec

🔁 规则:
rpmbuild --with feature--define 'with_feature 1'
rpmbuild --without feature--define 'without_feature 1'

多个条件宏示例:

sudo dnf builddep \
  --define 'with_mpich 1' \
  --define 'without_cuda 1' \
  your-package.spec

💡 提示:在 openEuler、CentOS Stream、Fedora、RHEL 8+ 等系统上均适用。


✅ 方法 B:手动安装缺失依赖

如果自动方法失败(如仓库中无对应包),可手动安装:

# 查看缺失的包名(从错误信息中获取)
sudo dnf install mpich-devel

# 若不确定包名,可搜索
dnf list available | grep -i mpich

openEuler 系统中,部分 HPC 包可能位于额外仓库(如 scshpc),可尝试启用:

sudo dnf config-manager --set-enabled scs
sudo dnf install mpich-devel

四、如何验证宏是否正确展开?

你可以预览 spec 文件在给定宏定义下的最终内容:

rpmspec -P --define 'with_mpich 1' your-package.spec | less
  • -P 表示“预处理”(preprocess),会展开所有宏和条件块。
  • 检查输出中是否包含 BuildRequires: mpich-devel,确认依赖已激活。

你也可以仅查看 BuildRequires 列表:

rpmspec -P --define 'with_mpich 1' your-package.spec | grep '^BuildRequires:'

五、完整操作流程示例

假设你要构建 your-package.spec 并启用 MPICH 支持:

# 1. 查看支持的条件宏
grep -E '%\{with_|%\{without_' your-package.spec

# 2. 安装构建依赖(启用 mpich)
sudo dnf builddep --define 'with_mpich 1' your-package.spec

# 3. (可选)验证宏展开结果
rpmspec -P --define 'with_mpich 1' your-package.spec | grep mpich-devel

# 4. 执行构建
rpmbuild -ba --with mpich your-package.spec

六、常见问题排查

问题 解决方案
dnf builddep 找不到包 确认是否启用了正确的软件源(如 EPEL、SCS、HPC)
宏名不匹配 注意 --with feature 对应的是 with_feature(下划线)
条件未生效 检查 spec 中是否写成 %if %{?with_feature}(带问号)或 %if %{with_feature}(不带)——两者行为略有不同
openEuler 上无 mpich-devel 尝试 sudo dnf install openmpi-devel 或从源码编译 MPICH

七、附录:常用命令速查

功能 命令
查找 spec 中的条件宏 `grep -E '%{with_
安装带条件的依赖 sudo dnf builddep --define 'with_xxx 1' pkg.spec
预览宏展开结果 `rpmspec -P --define 'with_xxx 1' pkg.spec
列出可用构建依赖包 `dnf list available

通过以上方法,可以高效处理由条件宏控制的 RPM 构建依赖,避免因依赖缺失导致的构建失败。

posted @ 2026-01-07 09:35  LoftyAmbition  阅读(3)  评论(0)    收藏  举报