恒美微站
首页
关于我们
建站服务
主题模板
案例展示
资讯中心
联系我们
CMake 文档开发指南:从 reStructuredText 源码到 `--help` 命令行帮助与 Sphinx 手册的完整管线
首页
资讯中心
/
CMake 文档开发指南:从 reStructuredText 源码到 `--help` 命令行帮助与 Sphinx 手册的完整管线
CMake 文档开发指南:从 reStructuredText 源码到 `--help` 命令行帮助与 Sphinx 手册的完整管线
发布时间:2026/10/5 6:50:38
构建工具开发工具CLI【免费下载链接】CMakeMirror of CMake upstream repository项目地址https://gitcode.com/gh_mirrors/cm/CMake点击查看免费下载本指南面向 CMake 开发者与文档贡献者系统讲解 CMake 帮助文档的源码组织、本地构建方法、--help-*命令行帮助处理器cmRST所支持的标记子集、cmakeSphinx Domain 的对象模型与指令、交叉引用语法以及文档风格规范并延伸介绍 Modules 目录中.cmake模块文档的编写流程。读完本文你将能够从Help/与Modules/源码出发独立编写、校验并构建出 HTML、man 页与命令行帮助三种输出形态的 CMake 文档。Help 目录CMake 手册的唯一事实来源CMake 的帮助手册源码全部位于仓库顶层的Help目录中包含命令Help/command/、模块Help/module/、策略Help/policy/、变量Help/variable/、属性Help/prop_*系列目录、生成器Help/generator/、环境变量Help/envvar/、手册页Help/manual/等分类文档。这些源码文件使用 reStructuredTextRST标记语法编写并由 Sphinx 处理生成 CMake 帮助手册。也就是说Help目录是 HTML 在线手册、man 手册、以及cmake --help-*命令行输出的共同事实来源。开发者想要了解文档开发的其他约定可进一步阅读 Help/dev/README.rst即本文所述的 CMake Development 文档。本地构建 HTML 与 man 手册文档构建入口位于Utilities/Sphinx这是一个独立的 CMake 项目。在 CMake 仓库内本地生成 HTML 与 man 手册到build/html与build/man目录只需两条命令$ cmake -S Utilities/Sphinx -B build -DSPHINX_HTMLON -DSPHINX_MANON $ cmake --build build如果系统中 Sphinx 的安装位置不在默认搜索路径可以显式指定$ cmake -S Utilities/Sphinx -B build -DSPHINX_HTMLON -DSPHINX_MANON \ -DSPHINX_EXECUTABLE/path/to/sphinx-build从构建脚本 Utilities/Sphinx/CMakeLists.txt 可以看到SPHINX_EXECUTABLE通过find_program查找名为sphinx-build的可执行文件除 HTML 与 man 之外该脚本还提供了一系列可选的文档输出格式开关CMake 选项输出内容SPHINX_HTMLHTML 手册安装到doc目录sphinx-html组件SPHINX_MANman 手册按Help/manual/*.[1-9].rst逐一安装到 man 分区SPHINX_SINGLEHTML单页 HTML 手册SPHINX_LINKCHECK检查文档中的外部链接SPHINX_QTHELPQt 帮助需要qhelpgeneratorSPHINX_LATEXPDF基于 LaTeX 的 PDFSPHINX_TEXT纯文本帮助不安装SPHINX_INFOtexinfo / info 手册需要makeinfoSPHINX_HTML_COPYBUTTON启用 sphinx-copybutton 扩展其中 man 手册的安装会跳过未构建的ccmakeBUILD_CursesDialog关闭时与cmake-guiBUILD_QtDialog关闭时对应页面。构建完成后HTML 输出路径会以file://.../html/index.html的形式打印到控制台方便直接打开。可选的 Sphinx 第三方扩展构建 HTML 帮助时CMake 使用第三方扩展 [sphinx-copybutton]——它会在code-block指令渲染出的代码块角落添加一个可交互的复制按钮。要在本地生成带该扩展的文档按上文方式配置时额外加上$ cmake -S Utilities/Sphinx -B build -DSPHINX_HTMLON -DSPHINX_HTML_COPYBUTTONON需要注意该扩展必须安装在与SPHINX_EXECUTABLE相同的环境或系统中否则构建会因导入失败而报错。命令行帮助处理器cmRST 与受支持的标记构造除了用 Sphinx 生成 HTML/man 手册外CMake 还内置了一个用 C 实现的文档处理器用于为cmake --help-*系列命令行帮助选项输出文本。该处理器的实现位于 Source/cmRST.cxx由 Source/cmDocumentation.cxx 驱动例如cmake --help-module name会调用它解析对应模块源码中的.rst:注释。它只支持 reStructuredText 标记的一个子集。因此在编写或修改文档时除了关注 Sphinx 生成的 HTML 与 man 页效果还必须验证命令行帮助的输出效果。以下是 cmRST 支持的构造清单该清单必须与 cmRST 实现保持一致见 Source/cmRST.cxx 顶部构造的正则构造命令行帮助处理方式CMake Domain 指令command/envvar/genex/signature/variable/diagnostic按普通段落文本输出并解释CMake Domain 解释文本角色cross-reference roles替换为其链接文本其他角色原样输出不处理code-block指令去掉指令行缩进统一替换为一个空格后原样输出代码块include指令将所引用的文档内联输出以::结尾的段落后的字面块原样输出::块内容公共缩进替换为一个空格note指令按普通段落文本输出并解释parsed-literal指令去掉指令行按普通文本输出块内容保留解释productionlist指令按普通段落文本输出并解释replace指令定义\|substitution\|替换必须先定义后引用\|substitution\|引用执行替换替换文本中的换行全部转换为空格toctree指令将被引用的文档内联到引用文档中versionadded/versionchanged指令按普通段落文本输出并解释需要注意两个边界行为未在上表中列出的行内标记构造inline markup在命令行帮助输出中原样打印。文档作者应优先使用在源码形态下看起来正确的行内标记避免使用\转义尽量改用行内字面量inline literal。未匹配上述任何指令的显式标记块explicit markup block会从命令行输出中移除。除非是..纯注释Sphinx 同样会移除它们否则不要使用这类块。缩进的限制避免嵌套块cmRST 不识别块的嵌套缩进。具体后果是显式标记块只有不缩进在其他块内部时才会被识别以::结尾的段落之后的字面块如果不在顶层缩进级别可能吞掉其后所有缩进的行。实践中应尽量避免这两种情况保证命令行帮助与 HTML/man 输出的一致性。CMake Domain对象模型CMake 为 Sphinx 增加了一个名为cmake的 Sphinx DomainCMake Domain其 Python 实现位于 Utilities/Sphinx/cmake.pyCMakeDomain类定义了如下文档对象类型对象类型含义关联参考commandCMake 语言命令cmake(1)、cmake_policy()cpack_genCPack 打包生成器cpack(1)的-G选项envvar环境变量cmake-env-variables(7)手册、set()命令generatorCMake 原生构建系统生成器cmake(1)的-G选项genexCMake 生成器表达式cmake-generator-expressions(7)手册manualCMake 手册页如cmake(1)moduleCMake 模块cmake-modules(7)手册、include()命令policyCMake 策略cmake-policies(7)手册、cmake_policy()命令prop_cache/prop_dir/prop_gbl/prop_sf/prop_inst/prop_test/prop_tgt缓存/目录/全局/源文件/安装文件/测试/目标属性cmake-properties(7)手册、set_property()命令variableCMake 语言变量cmake-variables(7)手册、set()命令在cmake.py中这些对象类型在CMakeDomain.object_types中注册并为每种类型提供了同名的交叉引用角色roles。对象的两大来源CMake Domain 文档对象来自两个途径1. 文档自动变换document transformSphinx 的 CMake 扩展CMakeTransform见cmake.py会把每个命名为Help/type/file-name.rst形式的文档自动变换为一个类型为type的 domain 对象。对象名从文档标题提取标题须采用如下形式并出现在.rst文件顶部附近、早于任何以字母、数字、或$开头的其他行object-name -------------如果.rst文件中没有这种字面标题则对象名取file-name如果存在标题则要求file-name等于去掉所有与字符后的object-name对于$genex-name或$genex-name:...形式则要求file-name等于genex-name。例如 Help/module/AddFileDependencies.rst 只有一行.. cmake-module::指令真正的对象名来自模块文件内部的标题。2. CMake Domain 指令文档中也可以使用显式指令来定义部分对象类型可用指令包括command指令、envvar指令、genex指令、variable指令详见下文。没有对应指令的对象类型如module、policy、各类prop_*必须通过上述文档自动变换来定义。CMake Domain 指令详解CMake Domain 提供以下指令均需在 Sphinx 与 cmRST 两侧保持一致支持cmake.py中注册于CMakeDomain.directivescmRST.cxx中也有对应正则。command指令文档化一个 command 对象要求一个参数命令名.. command:: command-name This indented block documents command-name.envvar指令文档化一个 envvar 对象要求一个参数环境变量名.. envvar:: envvar-name This indented block documents envvar-name.genex指令文档化一个 genex 对象要求一个参数生成器表达式名.. genex:: genex-name This indented block documents genex-name.该指令还支持可选的:target:选项用于指定自定义目标名。但由于这会影响用:genex:角色引用该对象的能力该选项应极少使用。signature指令用于在Help/command/command-name.rst文档中记载 CMake 命令签名.. signature:: command-name(signature) This indented block documents one or more signatures of a CMake command.该指令要求一个参数签名摘要并遵循如下规则::之后必须紧跟一个或多个签名第一个签名可以选择放在同一行。若指令后紧跟空行会产生文档生成错误1 argument(s) required, 0 supplied。签名可以跨多行但每个签名的最后一个)必须是该行的最后一个字符。签名之间不允许空行空行之后的内容被视为描述文字。签名中的空白不会被保留。要记载复杂签名时在signature指令参数中写缩写形式并在描述中用code-block写出完整签名。目标名称target生成规则默认目标名自动从签名中开头的 keyword 参数提取——keyword 指任何以字母开头、不含空格的序列。例如签名string(REGEX REPLACE match-regex ...)生成目标REGEX REPLACE等价于.. _\REGEX REPLACE:。也可以用:target:选项指定自定义目标名每个签名一行例如.. signature:: cmake_path(GET path-var ROOT_NAME out-var) cmake_path(GET path-var ROOT_PATH out-var) :target: GET ROOT_NAME GET ROOT_PATH第一个目标可以放在:target:同一行。如果目标名已在文档更早位置使用则不再生成超链接目标。目标可在同一文档内用REF_或TEXT REF__语法引用与 RST 章节标题一样这些目标不适用于 Sphinx:ref:语法但可以用例如:command:string(APPEND) 的形式全局引用。换行控制:break:选项虽然签名中的空白不被保留但默认情况下方括号或尖括号内部的换行会被抑制。该行为可通过:break:选项控制取值如下取值行为all允许在任何空白处换行smart默认允许在空白处换行但配对的方/尖括号之间除外。例如\input\... [OUTPUT_VARIABLE \out-var\]中允许在input...之后换行但不允许在OUTPUT_VARIABLE与out-var之间换行verbatim仅在源码文档存在换行处换行注意没有任何方式可以强制换行。指令内容即签名文档需相应缩进。variable指令文档化一个 variable 对象要求一个参数变量名.. variable:: variable-name This indented block documents variable-name.交叉引用机制Sphinx 使用 reStructuredText 解释文本角色提供交叉引用语法。CMake Domain 为每种对象类型提供了同名角色形式为:type:name :type:text name其中type是 domain 对象类型name是对象名。第一种形式链接文本为name若类型为command则为name()第二种形式链接文本为显式的text。例如* The :command:list command. * The :command:list(APPEND) sub-command. * The :command:list() command list. * The :command:list(APPEND) sub-command list. * The :variable:CMAKE_VERSION variable. * The :prop_tgt:OUTPUT_NAME_CONFIG target property.尖括号的语义差异CMake Domain 角色与 Sphinx/reStructuredText 惯例有一个重要区别不带空格的ab形式被解释为名字而非链接文本 显式目标。这是必要的因为对象名中频繁使用占位符如OUTPUT_NAME_CONFIG。而带空格的a b形式仍解释为链接文本 显式目标。此外cref角色可用于创建指向本地目标、并带有字面量样式的引用特别适合在命令文档中引用其子命令。实现上CMakeCRefRolecmake.py直接使用nodes.reference加nodes.literal渲染而CMakeXRefRole则处理:command:、:genex:、:guide:等角色的语法展开与索引登记。文档风格规范为保证全部文档形态的一致观感CMake 文档有明确的风格约定。章节标题标题装饰线长度与标题文本等长只画在标题下方不画在上方Title Text ----------标题中每个非次要单词的首字母大写。标题下划线字符层级自上而下为字符用途#总文档中的手册分组part*手册chapter标题手册内的章节section-子章节或 CMake Domain 对象文档标题^子子章节或 CMake Domain 对象文档的小节段落或 CMake Domain 对象文档的子小节~CMake Domain 对象文档的子子小节空白与行宽缩进使用两个空格。散文prose中句子之间使用两个空格。行宽尽量限制在 75–80 列这不是硬性限制但新段落按 75 列换行能为后续小幅增补留出空间避免大幅重排。行内字面量对签名中的关键字、文件名及其他技术术语使用inline-literal语法标记。例如If WIN32 is used with :command:add_executable, the :prop_tgt:WIN32_EXECUTABLE target property is enabled. That command creates the file name.exe on Windows.命令签名写法约定在Help/command/command-name.rst文档中使用 CMake Domain 的signature指令为每个签名单独建档用章节标题把签名与前置内容分隔开例如... preceding paragraph. Normal Libraries ^^^^^^^^^^^^^^^^ .. signature:: add_library(lib ...) This signature is used for ...签名文档的约定用尖括号placeholder表示由调用方指定的参数正文中用行内字面量语法引用它们可选部分用方括号包裹可重复部分以省略号...结尾同一命令的不同签名可多次使用signature指令。布尔常量用户可修改的布尔值如POSITION_INDEPENDENT_CODE使用OFF与ON这些属性可以说 enabled/disabled。一经设置便不可修改的固有值如构建目标的IMPORTED属性使用True与False。交叉引用与概念引用所有可链接的引用都标记为链接包括重复出现的引用与 Wikipedia 一篇文章只链接一次 的风格不同CMake 文档不采用后者。当某个概念对应一个属性、且该概念在高层级手册中有描述时优先链接到手册章节而非属性。例如This command creates an :ref:Imported Target Imported Targets.而不是This command creates an :prop_tgt:IMPORTED target.后者仅当专门指该属性本身时才使用。手册章节不会因创建章节而自动生成引用目标需要显式锚点.. _Imported Targets:锚点名应与对应章节名一致并用带指定文本的交叉引用指向它。注意IMPORTED这个术语可能指命令关键字、目标属性或概念标记时需特别小心。另外属性、命令或变量若与其他概念相关例如与构建系统描述、生成器表达式或 Qt 相关每个相关对象都应链接到提供高层信息的主手册只有与该命令相关的特定信息才放在该命令的文档中。引用 CMake Domain 对象当引用属性、变量、命令等 CMake Domain 对象时优先链接到目标对象并紧跟其对象类型。例如Set the :prop_tgt:AUTOMOC target property to ON.而不是Set the target property :prop_tgt:AUTOMOC to ON.policy指令是例外类型通常放在链接之前If policy :policy:CMP0022 is set to NEW the behavior is ...另外文档中的自我引用使用inline-literal语法。例如在add_executable命令文档内部使用 add_executable而不是:command:add_executable后者用于其他位置的引用。模块文档编写Modules目录存放 CMake 语言的.cmake模块文件其文档同样由Help侧生成。注册流程要为Modules/module-name.cmake建档需要两步编辑 Help/manual/cmake-modules.7.rst在toctree指令中按排序顺序加入/module/module-name新增模块文档文件Help/module/module-name.rst其中只包含一行.. cmake-module:: ../../Modules/module-name.cmakecmake-module指令会扫描模块文件从以.rst:开头的注释块中提取 reStructuredText 标记该指令的解析逻辑见cmake.py中的CMakeModule类它同时支持括号注释与#.rst:行注释两种形态。模块文件内的文档注释在Modules/module-name.cmake顶部首先放置如下许可证声明# Distributed under the OSI-approved BSD 3-Clause License. See accompanying # file LICENSE.rst or https://cmake.org/licensing for details.声明之后加一个空行然后使用 Bracket Comment 形式书写文档#[[.rst: module-name ------------- reStructuredText documentation of module #]]规则要点开闭括号中可使用任意数量的只要两边匹配即可。如果闭合括号所在行以#开头则该行内容被排除不入文档。额外的.rst:注释可以出现在模块文件的任意位置但所有此类注释必须以#开头且位于第一列。一个完整的示例FindXxx.cmake模块# Distributed under the OSI-approved BSD 3-Clause License. See accompanying # file LICENSE.rst or https://cmake.org/licensing for details. #[[.rst: FindXxx ------- This is a cool module. This module does really cool stuff. It can do even more than you think. It even needs two paragraphs to tell you about it. And it defines the following variables: VAR_COOL this is great isnt it? VAR_REALLY_COOL cool right? #]] code #[[.rst: .. command:: Xxx_do_something This command does something for Xxx:: Xxx_do_something(some arguments) #]] macro(Xxx_do_something) code endmacro()仓库中的真实范例可对照 Modules/AddFileDependencies.cmake文件顶部是 BSD 许可证注释随后是一个.rst:Bracket Comment内含AddFileDependencies标题、deprecated提示、include(AddFileDependencies)用法示例以及.. command:: add_file_dependencies指令。校验与隐藏运行cmake --help-module module-name测试命令行帮助的排版效果同时开启SPHINX_HTML与SPHINX_MAN选项构建文档反复调整注释直到各形态输出都令人满意。如果希望某个.cmake文件不出现在模块文档中只需不添加Help/module/module-name.rst文件、也不在Help/manual/cmake-modules.7.rst的toctree中登记它即可。模块内函数与宏的命名规范模块可以提供由function()与macro()命令定义的 CMake 函数和宏。为避免跨模块冲突命名约定为使用ModuleName_前缀ModuleName为模块名的精确大小写拼写加上其余名称前缀之后的部分没有统一约定。出于历史原因CMake 自带的部分模块并未遵循此前缀约定。为这些模块新增函数时在评审讨论中可决定是遵循其既有约定还是改用模块名前缀。公开函数与宏的文档应写在模块中通常放在顶部的主文档区域。例如MyModule模块可这样文档化一个函数#[[.rst: MyModule -------- This is my module. It provides some functions. .. command:: MyModule_Some_Function This is some function: .. code-block:: cmake MyModule_Some_Function(...) #]]文档也可以放在每个定义之前。例如另一个函数#[[.rst: .. command:: MyModule_Other_Function This is another function: .. code-block:: cmake MyModule_Other_Function(...) #]] function(MyModule_Other_Function ...) # ... endfunction()文档管线全景三种输出的源码印证综合全文CMake 文档从源码到三种输出的完整管线如下HTML / man / 其他 Sphinx 格式由 Utilities/Sphinx/CMakeLists.txt 生成构建规则configure_file生成conf.py再调用sphinx-build以Help目录为源进行构建。cmake.py中的setup()注册了cmake-module指令、CMakeTransform变换、CMakeXRefTransform变换与CMakeDomain。命令行帮助由 C 实现的 Source/cmRST.cxx 解析 RST 子集Source/cmDocumentation.cxx 负责cmake --help-*的输出其指令与角色正则CMakeDirective、CMakeRole、CodeBlockDirective、VersionDirective、ModuleRST等与文档中列出的构造清单一一对应。模块对象索引CMakeTransform依据Help/type/file-name.rst的路径前缀自动登记 domain 对象并建立索引条目cmake.py中的_cmake_index_objs表则定义了各对象类型在 Sphinx 索引中的呈现名称如command、cache property、target property等。此外CMakeSignatureObject在cmake.py中实现了:break:选项的all/smart/verbatim三种换行策略_break_signature_all/_break_signature_smart/_break_signature_verbatim并利用 pygments 的 CMakeLexer 对签名做语法高亮这与文档中签名空白不保留、括号内抑制换行的描述完全对应。理解了这条双处理器Sphinx cmRST管线即可在新增或修改任何 CMake 文档时一次性保证 HTML、man 与命令行帮助三种形态的行为一致。赞分享构建工具开发工具CLI【免费下载链接】CMakeMirror of CMake upstream repository项目地址https://gitcode.com/gh_mirrors/cm/CMake点击查看免费下载相关推荐Infer help 子命令完全指南从命令行手册到网站文档生成Infer help 子命令完全指南从命令行手册到网站文档生成 导读 infer help 是 Infer 静态分析器内置的文档子命令它既承担着命令行手册静态分析代码质量开发工具asdf 命令全景手册从 asdf help 到源码级解析的完整命令指南asdf 命令全景手册从 asdf help 到源码级解析的完整命令指南 asdf 是一个可扩展的多运行时版本管理器通过统一的命令接口管理 Ruby、NodCLI开发工具Sphinx reStructuredText 完全指南从语法基础到高级指令的实战手册Sphinx reStructuredText 完全指南从语法基础到高级指令的实战手册 reStructuredTextreST是 Sphinx 文档生成文档开发工具上一篇为什么选择TorchNPUPyTorch昇腾NPU深度学习适配插件新手完全指南下一篇TradingAgents-CN 分析任务预计总时长不一致问题修复全解析从数据源混用到同源一致创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考