-pr:h指定host profile,决定目标产物的ABI、架构等;-pr:b指定build profile,只影响本地构建缺失二进制时的编译工具链配置。

conan install 的 -pr:h 和 -pr:b 分别控制什么
Conan 的 build 和 host 配置不是“编译阶段 vs 运行阶段”这种模糊说法,而是严格对应两个独立的构建上下文:一个负责**构建工具链本身**(build),另一个负责**目标产物**(host)。你执行 conan install 时,必须明确指定哪个 profile 是给谁用的。
-
-pr:h(host profile)决定最终可执行文件或库的 ABI、架构、标准库、C++ 版本等——也就是你的项目二进制要跑在哪种环境上。它直接参与每个依赖包的package ID计算,比如os=Linux+arch=x86_64+build_type=Debug组合出唯一 ID。 -
-pr:b(build profile)只影响 Conan 在本地**如何构建缺失的二进制**(例如远程没有fmt/10.2.1的armv8+Release包,Conan 就得自己编)。它定义的是你这台机器上用来编译的编译器、sysroot、链接器路径等——和最终产物无关,但决定了能不能成功编出来。 - 如果你没传
-pr:b,Conan 默认用defaultprofile 当 build profile;但它很可能和你的 host 不兼容(比如 host 是armv8,default 是x86_64),导致--build=missing失败并报错Cannot build package 'xxx' for settings 'os=Linux, arch=armv8...' with build profile 'os=Linux, arch=x86_64...'。
为什么 CMake 的 CMAKE_BUILD_TYPE 不能代替 build_type settings
很多人以为在 CMake 命令里加 -DCMAKE_BUILD_TYPE=Debug 就够了,结果发现依赖库还是 Release 版本——这是因为 Conan 的 build_type 是 settings,属于包身份的一部分;而 CMake 的 CMAKE_BUILD_TYPE 只是生成器内部的变量,不会自动同步到 Conan 的 host profile 里。
- 对单配置生成器(Ninja / Makefiles),你必须确保
-DCMAKE_BUILD_TYPE=Debug和 host profile 中的build_type=Debug一致,否则CMakeToolchain生成的编译标志(如-O0 -g)和实际链接的库(可能是Release版本)不匹配,轻则性能异常,重则符号未定义或 ABI 崩溃。 - 对多配置生成器(MSVC),CMake 不依赖
CMAKE_BUILD_TYPE,而是靠--config Debug切换;此时 Conan 的 host profile 仍需设为build_type=Debug,否则CMakeDeps找不到对应配置的fmtConfig.cmake文件,报错find_package(fmt CONFIG REQUIRED) failed。 - 最稳妥的做法:把
build_type写死在 host profile 里,而不是靠命令行传参临时覆盖——避免 CI 脚本漏写或拼错。
profile 文件里哪些字段属于 build,哪些属于 host
同一个 profile 文件可以同时含 build 和 host 字段,但只有被 -pr:h 或 -pr:b 显式引用时,其中的设置才生效。关键区分点在于:是否影响目标产物的 ABI 兼容性。
- 属于
host的典型字段:os、arch、compiler、compiler.version、compiler.libcxx、build_type、compiler.cppstd——这些全都会进入 package ID,决定你拉哪个二进制。 - 属于
build的典型字段:tools.build:sysroot、tools.cmake.cmaketoolchain:generator、tools.cmake.cmaketoolchain:toolset、tools.microsoft.msbuild:architecture——它们只影响 Conan 自己怎么调用编译器,不参与依赖包选择。 - 容易踩坑的是
tools.build:compiler_executables:它看起来像编译器设置,但其实是告诉 Conan “用哪个gcc去编交叉包”,应放在buildprofile 里;如果错放 host profile,会导致 Conan 尝试用aarch64-gcc去编 host 本机的spdlog,直接失败。
什么时候必须用双 profile,什么时候可以省略 -pr:b
是否需要显式指定 -pr:b 取决于你有没有“构建行为”——即是否允许 Conan 从源码编包(--build=missing 或 --build=outdated)。如果所有依赖都已有预编译二进制,-pr:b 就完全不参与流程。
- 必须用双 profile 的场景:
conan install . --build=missing -pr:h=profiles/arm64-release -pr:b=profiles/linux-x86_64-gcc12——你目标是 ARM64,但构建机是 x86_64 Linux,必须分开指定。 - 可以省略
-pr:b的场景:conan install . -pr:h=profiles/win64-msvc——远端已有完整二进制,Conan 只下载不编,buildprofile 根本不加载。 - 最容易忽略的一点:CI 流水线中,即使你只做
conan install,也要检查是否启用了--build=相关参数(比如某些模板默认加--build=missing),否则本地能过,CI 上因 build profile 缺失而卡住。


















