target_precompile_headers

在 3.16 版本中添加。

添加要预编译的头文件列表。

预编译头文件可以通过创建某些头文件的部分处理版本来加速编译,然后在编译期间使用该版本,而不是重复解析原始头文件。

主要形式

target_precompile_headers(<target>
  <INTERFACE|PUBLIC|PRIVATE> [header1...]
  [<INTERFACE|PUBLIC|PRIVATE> [header2...] ...])

此命令将头文件添加到 PRECOMPILE_HEADERS 和/或 INTERFACE_PRECOMPILE_HEADERS 目标属性 <target>。命名的 <target> 必须已通过诸如 add_executable()add_library() 之类的命令创建,并且不得为 别名目标

INTERFACEPUBLICPRIVATE 关键字是必需的,用于指定以下参数的 作用域PRIVATEPUBLIC 项将填充 <target>PRECOMPILE_HEADERS 属性。PUBLICINTERFACE 项将填充 <target>INTERFACE_PRECOMPILE_HEADERS 属性(导入目标 仅支持 INTERFACE 项)。对同一 <target> 的重复调用将按调用顺序追加项。

项目通常应避免对将要 导出 的目标使用 PUBLICINTERFACE,或者他们至少应使用 $<BUILD_INTERFACE:...> 生成器表达式来防止预编译头文件出现在已安装的导出目标中。目标的消费者通常应控制他们使用的预编译头文件,而不是让被消费的目标强制他们使用预编译头文件(因为预编译头文件通常不是使用要求)。一个值得注意的例外是创建 接口库 以在一个位置定义一组常用的预编译头文件,然后其他目标私下链接到该接口库。在这种情况下,接口库的存在专门用于将其预编译头文件传播给其消费者,并且消费者实际上仍然处于控制之中,因为它决定是否链接到接口库。

头文件列表用于生成名为 cmake_pch.h|xx 的头文件,该文件用于生成预编译的头文件(.pch.gch.pchi)工件。cmake_pch.h|xx 头文件将被强制包含(GCC 的 -include,MSVC 的 /FI)到所有源文件中,因此源文件不需要有 #include "pch.h"

用尖括号(例如 <unordered_map>)或显式双引号(为 cmake-language(7) 转义,例如 [["other_header.h"]])指定的头文件名将按原样处理,并且包含目录必须可用于编译器才能找到它们。其他头文件名(例如 project_header.h)被解释为相对于当前源目录(例如 CMAKE_CURRENT_SOURCE_DIR),并将通过绝对路径包含。例如

target_precompile_headers(myTarget
  PUBLIC
    project_header.h
  PRIVATE
    [["other_header.h"]]
    <unordered_map>
)

有关定义构建系统属性的更多信息。

target_precompile_headers 的参数可以使用语法 $<...> 的生成器表达式。请参阅 cmake-generator-expressions(7) 手册以获取可用的表达式。$<COMPILE_LANGUAGE:...> 生成器表达式对于仅为一种语言(例如 CXX 而不是 C)指定要预编译的特定语言头文件特别有用。在这种情况下,未显式用双引号或尖括号引起来的头文件名必须通过绝对路径指定。此外,当在生成器表达式中指定尖括号时,请务必将右尖括号 > 编码为 $<ANGLE-R>。例如

target_precompile_headers(mylib PRIVATE
  "$<$<COMPILE_LANGUAGE:CXX>:${CMAKE_CURRENT_SOURCE_DIR}/cxx_only.h>"
  "$<$<COMPILE_LANGUAGE:C>:<stddef.h$<ANGLE-R>>"
  "$<$<COMPILE_LANGUAGE:CXX>:<cstddef$<ANGLE-R>>"
)

重用预编译头文件

该命令还支持第二种签名,该签名可用于指定一个目标重用来自另一个目标的预编译头文件工件,而不是生成自己的工件

target_precompile_headers(<target> REUSE_FROM <other_target>)

此形式将 PRECOMPILE_HEADERS_REUSE_FROM 属性设置为 <other_target>,并添加一个依赖项,以便 <target> 将依赖于 <other_target>。如果在使用 REUSE_FROM 形式时,<target>PRECOMPILE_HEADERS 属性已设置,则 CMake 将停止并报错。

注意

REUSE_FROM 形式要求 <target><other_target> 具有相同的编译器选项、编译器标志和编译器定义。如果无法使用预编译的头文件,某些编译器(例如 GCC)可能会发出警告(-Winvalid-pch)。

参见