Linux 内核文档构建指南:使用 Sphinx 与 reStructuredText 编写和生成内核文档

Linux 内核文档构建指南:使用 Sphinx 与 reStructuredText 编写和生成内核文档 Linux 内核文档构建指南使用 Sphinx 与 reStructuredText 编写和生成内核文档【免费下载链接】linuxLinux kernel source tree项目地址: https://gitcode.com/GitHub_Trending/li/linux本篇技术指南聚焦于 Linux 内核源码树中Documentation目录的文档体系内核如何借助 Sphinx 将 reStructuredTextreST源文件编译为 HTML、PDF 等多种格式如何在源码注释中嵌入 kernel-doc 结构化注释以及贡献者在撰写内核文档时必须遵循的标记规范标题装饰、表格语法、交叉引用、图片指令等。读完本文你将掌握从环境准备、依赖检查、执行make htmldocs/make pdfdocs构建到新增.rst文档并接入主 TOC 树的完整流程并能基于 Documentation/doc-guide/sphinx.rst 与仓库中的实际实现如 Documentation/Makefile、Documentation/conf.py、Documentation/sphinx/kfigure.py写出符合内核社区规范的文档。内核文档体系概览Linux 内核使用 Sphinx 从Documentation目录下的 reStructuredText 文件生成排版精美的文档。构建 HTML 或 PDF 只需运行make htmldocs或make pdfdocs生成结果统一输出到Documentation/output目录。内核文档体系由三类内容组成reStructuredText 源文件分布于Documentation目录是 Sphinx 构建的主体输入kernel-doc 注释reST 文件可以通过指令directive将源码文件中的结构化注释kernel-doc comments包含进来用于描述函数的原型、类型设计与代码设计意图。kernel-doc 注释有特殊的结构与格式化要求除此之外它们同样按 reStructuredText 解析纯文本文档Documentation下还散落着数以千计的纯文本文件。其中一部分会随着时间推移逐步转换为 reStructuredText但大部分仍会保持纯文本形式。Sphinx 安装当前Documentation/使用的 reST 标记要求 Sphinx 版本3.4.3 或更高。这一约束在仓库中有两处硬性体现Documentation/conf.py 中needs_sphinx 3.4.3以及 tools/docs/sphinx-pre-install 中RECOMMENDED_VERSION PythonVersion(3.4.3)。大多数发行版都预装了 Sphinx但它的工具链较为脆弱升级 Sphinx 或机器上的其他 Python 包都可能导致文档构建失败。推荐的规避方案是使用与发行版不同的版本即将 Sphinx 安装到 Python 虚拟环境中。根据发行版打包 Python 3 的方式使用virtualenv-3或virtualenv$ virtualenv sphinx_latest $ . sphinx_latest/bin/activate (sphinx_latest) $ pip install -r Documentation/sphinx/requirements.txt执行. sphinx_latest/bin/activate后提示符会变化以标识当前处于新环境中如果打开了新的 shell需要重新执行该命令以再次进入虚拟环境然后再构建文档。Documentation/sphinx/requirements.txt 内容非常精简仅包含三个包alabaster Sphinx pyyaml其中alabaster正是文档中提到的默认 HTML 主题随 Sphinx 一并安装无需单独安装。图像输出内核文档构建系统包含一个扩展用于处理GraphVizDOT与SVG格式的图像详见下文kernel-figure指令。要使图像功能正常工作需要安装 GraphViz 和 ImageMagick 两个软件包。若未安装这些包构建仍会照常进行只是输出中不包含任何图像。PDF 与 LaTeX 构建PDF / LaTeX 构建仅受 Sphinx 2.4 及以上版本支持且还需要XeLaTeX版本 3.14159265。具体到发行版通常还需要安装一系列提供 XeLaTeX 最小功能集的texlive软件包。在 Documentation/Makefile 中可以看到 PDF 构建直接使用PDFLATEX xelatex。另外文档的脚注特别提到若同时安装了 Inkscape 的inkscape(1)将能提升 PDF 文档中内嵌图像的质量尤其针对内核 5.18 及以后版本的文档。HTML 中的数学表达式部分 reST 页面包含数学表达式。由于 Sphinx 的工作方式这些表达式使用 LaTeX 记法书写。Sphinx 提供两种在 HTML 输出中渲染数学表达式的扩展imgmath将数学表达式转换为图片并嵌入 HTML 页面mathjax将数学渲染委托给支持 JavaScript 的浏览器。前者是6.1 之前内核文档唯一的选项且需要相当多的 texlive 软件包包括 amsfonts、amsmath 等。自内核 6.1 发布起包含数学表达式的 HTML 页面可以无需安装任何 texlive 软件包即可构建详情见下文数学渲染器的选择一节。检查 Sphinx 依赖仓库提供了一个自动检查 Sphinx 依赖的脚本 tools/docs/sphinx-pre-install。如果它能识别出你的发行版还会给出针对该发行版的安装命令提示$ ./tools/docs/sphinx-pre-install Checking if the needed tools for Fedora release 26 (Twenty Six) are available Warning: better to also install texlive-luatex85. You should run: sudo dnf install -y texlive-luatex85 /usr/bin/virtualenv sphinx_2.4.4 . sphinx_2.4.4/bin/activate pip install -r Documentation/sphinx/requirements.txt Cant build as 1 mandatory dependency is missing at ./tools/docs/sphinx-pre-install line 468.默认情况下它会检查HTML 与 PDF 的所有需求包括图像、数学表达式和 LaTeX 构建所需项并假定使用 Python 虚拟环境HTML 构建所需项被假定为强制mandatory其余被假定为可选optional。这一点与脚本源码中DepManager对依赖三分类System / Python / PDF以及 mandatory / optional 属性的设计一致见 tools/docs/sphinx-pre-install。脚本支持两个可选参数参数作用--no-pdf禁用对 PDF 相关依赖的检查--no-virtualenv使用操作系统打包的 Sphinx而非 Python 虚拟环境值得一提的是Documentation/Makefile 在每次执行htmldocs等构建目标前都会先调用sphinx-pre-install --version-check做版本校验若sphinx-build不在 PATH 中还会自动提示运行该脚本并跳过构建目标。安装 Sphinx 最低版本开发验证当修改 Sphinx 构建系统时确保最低版本仍然受支持至关重要。如今在较新的发行版上这越来越困难——例如 Python 3.13 及以上无法安装旧版 Sphinx。按 Documentation/process/changes.rst 定义的最低受支持 Python 版本进行测试可创建对应的 venv 并安装最低依赖集/usr/bin/python3.9 -m venv sphinx_min . sphinx_min/bin/activate pip install -r Documentation/sphinx/min_requirements.txtDocumentation/sphinx/min_requirements.txt 给出了精确到小版本号的完整约束例如Sphinx3.4.3、docutils0.15,0.18、jinja22.3,3.1、PyYAML5.1,6.1以及alabaster 0.7,0.8等确保在最低版本下也能锁定可复现的构建环境。更全面的测试可以使用脚本 tools/docs/test_doc_build.py。该脚本会为每个受支持的 Sphinx 版本创建一个独立的 Python venv并可选择性地对一系列 Sphinx 版本逐一执行文档构建。从其默认测试矩阵可见构建系统的支持范围从最低版本(3, 4, 3)起覆盖 Debian 12Sphinx 6.1.1、Ubuntu 24.04 LTS7.2.6、Fedora 428.1.3乃至最新版本8.2.3等主流发行版场景见 tools/docs/test_doc_build.py。Sphinx 构建生成文档的常规方式是运行make htmldocs或make pdfdocs还有更多其他格式可用——参见make help的文档一节。生成的文档位于Documentation/output下按格式区分的子目录中。这一行为由 Documentation/Makefile 中的BUILDDIR $(obj)/output定义。构建文档显然需要安装 Sphinxsphinx-buildPDF 输出还需要 XeLaTeX 与 ImageMagick 的convert(1)。这些工具在各发行版中普遍可得。常用 make 变量构建系统暴露了若干 make 变量用于控制构建行为这些变量全部定义在 Documentation/Makefile 中make 变量用途示例SPHINXOPTS向 Sphinx 传递额外选项make SPHINXOPTS-v htmldocs输出更详细的构建日志DOCS_CSS传入额外的 CSS 覆盖文件自定义 HTML 布局make DOCS_CSSmy.css htmldocsDOCS_THEME覆盖默认的 Sphinx 主题make DOCS_THEMEsphinx_rtd_theme htmldocsSPHINXDIRS只构建指定子目录的文档子集make SPHINXDIRSdoc-guide htmldocsSPHINXBUILD指定sphinx-build可执行文件路径默认sphinx-build—PAPER指定 LaTeX/PDF 输出的纸张大小make PAPERa4 pdfdocs默认情况下使用Alabaster主题构建 HTML该主题随 Sphinx 捆绑无需单独安装。若想覆盖主题可用DOCS_THEME变量。文档的备注提示部分开发者偏好 RTD 主题Read the Docs视 Sphinx 版本不同可能需要单独安装即pip install sphinx_rtd_theme。SPHINXDIRS对测试构建文档子集特别有用。例如只构建Documentation/doc-guide下的文档make SPHINXDIRSdoc-guide htmldocsmake help的文档一节会列出所有可指定的子目录该列表由 Documentation/Makefile 动态扫描Documentation/*/index.rst生成。SPHINXDIRS也支持更深层的子目录例如SPHINXDIRSuserspace-api/media前提是该子目录下存在index.rst文件。清理生成的文档运行make cleandocs对应 Documentation/Makefile 中删除整个BUILDDIR的操作。此外构建系统还提供了一系列独立目标例如linkcheckdocs检查外部链接连通性会连接外部主机、refcheckdocs检查Documentation下对不存在文件的引用、htmldocs-redirects为移动过的页面生成 HTML 重定向等全部清单可通过make dochelp查看。数学渲染器的选择自内核 6.1 起mathjax 作为 HTML 输出的回退数学渲染器工作该回退机制要求 Sphinx 1.8。渲染器的选择取决于当前可用的命令数学渲染器必需命令图片格式imgmathlatex, dvipngPNG位图mathjax无额外依赖浏览器端渲染—可以通过设置环境变量SPHINX_IMGMATH覆盖默认选择设置渲染器SPHINX_IMGMATHyesimgmathSPHINX_IMGMATHnomathjax这解释了为何 6.1 之后构建含数学公式的 HTML 页面不再需要 texlive 软件包只要未显式强制使用 imgmath构建系统会优先选择零系统依赖的 mathjax 路径。编写文档新增文档可以简单到只需两步在Documentation下某个位置新增一个.rst文件在 Sphinx 主 TOC 树 Documentation/index.rst 中引用它。对于简单的文档例如本指南本身这通常已经足够但对于大型文档建议创建子目录或使用已有子目录。例如图形子系统文档位于 Documentation/gpu拆分为多个.rst文件并拥有独立的index.rst含自己的toctree再由主索引引用。从 Documentation/index.rst 可以看到这种组织方式顶层通过多个toctree将 process、core-api、driver-api、doc-guide 等子手册挂载到主文档树。关于 Sphinx 与 reStructuredText 的更多能力参见 Sphinx 官方文档及其 reStructuredText PrimerSphinx 特定的标记结构也有专门的参考页。内核文档的具体准则撰写内核文档时请遵循以下具体规范不要过度使用 reStructuredText 标记。保持简单文档主体应当是可读的纯文本只需保持足够一致的格式以便转换到其他格式将现有文档转换为 reStructuredText 时尽量保持格式改动最小转换文档时不仅更新格式还要更新内容严格遵循标题装饰的固定顺序文档标题用加顶线overline Document title 章节Chapters用Chapters 小节Sections用-Section -------子小节Subsections用~Subsection ~~~~~~~~~~虽然 reST 并未强制规定固定顺序与其强加固定的标题装饰样式数量与顺序不如按照实际遇到的顺序执行但让较高级别标题保持整体一致会使文档更易阅读。插入等宽文本块时凡不需要语法高亮的场景尤其是短片段使用::较长的、适合高亮的代码块使用.. code-block:: language正文中嵌入的短代码片段使用反引号包裹。C DomainC 语言域Sphinx C Domain名字为c适合记录 C API。例如一个函数原型.. c:function:: int ioctl( int fd, int request )内核文档的 C Domain 还有一些附加特性。例如可以把open、ioctl这类常见名字的引用名ref-name重命名.. c:function:: int ioctl( int fd, int request ) :name: VIDIOC_LOG_STATUS函数名如ioctl仍保留在输出中但引用名从ioctl变为VIDIOC_LOG_STATUS该函数在索引中的条目也随之改为VIDIOC_LOG_STATUS。需要注意无需使用c:func:来生成指向函数文档的交叉引用。得益于 Sphinx 扩展的自动标记机制automarkup构建系统会自动把文档中对function()形式的引用转换为交叉引用——只要该函数名存在对应的索引条目。Documentation/sphinx/automarkup.py 中正是通过正则RE_function re.compile(r\b(([a-zA-Z_]\w)\(\)))匹配xxx()形式文本并转换为 C 域引用同理struct/union/enum/typedef关键字后的标识符RE_struct、RE_union等也会被自动标记为代码样式并交叉引用。因此如果在内核文档中看到c:func:的使用可以放心地将其移除。该扩展还维护了一个Skipfuncs列表如open、ioctl、mmap等常见系统调用名避免误生成无意义的交叉引用见 Documentation/sphinx/automarkup.py。表格reStructuredText 提供了多种表格语法。内核风格的表格优先使用简单表格simple table或网格表格grid table语法细节参见 reStructuredText 表格语法用户参考。list-table 与 flat-tablelist-table格式适用于难以用 Sphinx ASCII-art 表格排布的表格但这种格式对纯文本读者几乎无法理解除非有充分理由否则应避免使用。flat-table是一种类似list-table的两级列表但附加了若干特性列合并column-span通过角色cspan一个单元格可横向跨越额外的列行合并row-span通过角色rspan一个单元格可纵向跨越额外的行自动跨越auto span默认将表格行最右侧的单元格自动扩展到该行右侧缺失的单元格。使用选项:fill-cells:可将行为从auto span改为auto fill——自动插入空单元格而不是跨越最后一个单元格。flat-table的选项选项取值说明:header-rows:[int]表头行数:stub-columns:[int]桩列stub列数:widths:[[int] [int] ...]各列宽度:fill-cells:—在缺失单元格处插入空单元格而不是自动跨越角色角色取值说明:cspan:[int]额外跨越的列数morecols:rspan:[int]额外跨越的行数morerows下面的例子展示了如何使用该标记。两级列表的第一级是table-row在table-row中只允许一种标记——该行的单元格列表。例外情况是注释..与目标target例如:ref:last row 形式的引用。.. flat-table:: table title :widths: 2 1 1 3 * - head col 1 - head col 2 - head col 3 - head col 4 * - row 1 - field 1.1 - field 1.2 with autospan * - row 2 - field 2.1 - :rspan:1 :cspan:1 field 2.2 - 3.3 * .. _last row: - row 3渲染效果如下.. flat-table:: table title :widths: 2 1 1 3* - head col 1 - head col 2 - head col 3 - head col 4 * - row 1 - field 1.1 - field 1.2 with autospan * - row 2 - field 2.1 - :rspan:1 :cspan:1 field 2.2 - 3.3 * .. _last row: - row 3flat-table指令由 Documentation/sphinx/rstFlatTable.py 实现构建系统会自动加载该扩展。交叉引用从一个文档页面交叉引用到另一个页面只需写出目标文档文件的路径无需任何特殊语法。路径可以是绝对路径或相对路径。绝对路径以Documentation/开头。例如要引用本页面根据当前文档所在目录以下写法都合法注意.rst扩展名是必需的See Documentation/doc-guide/sphinx.rst. This always works. Take a look at sphinx.rst, which is at this same directory. Read ../sphinx.rst, which is one directory above.这一点同样由automarkup扩展的RE_doc正则匹配Documentation/...形式路径自动完成标记与链接见 Documentation/sphinx/automarkup.py。如果希望链接显示为不同于文档标题的文字需要使用 Sphinx 的doc角色例如See :doc:my custom link text for document sphinx sphinx.大多数场景下优先使用前者直接写路径因为它更简洁也更适合直接阅读源码的人。如果看到没有实际价值的:doc:用法可以放心地将其转换为纯文档路径。关于交叉引用 kernel-doc 函数或类型的信息参见 Documentation/doc-guide/kernel-doc.rst。引用 commit对 git commit 的引用会被自动添加超链接只要以以下任一格式书写commit 72bf4f1767f0 commit 72bf4f1767f0 (net: do not leave an empty skb in write queue)这一行为同样由automarkup中的RE_git正则实现匹配commit加 12–40 位十六进制哈希可带可选的引号消息见 Documentation/sphinx/automarkup.py。图形与图像添加图像时应使用kernel-figure与kernel-image指令。例如插入一张可缩放格式SVG的图.. kernel-figure:: svg_image.svg :alt: simple SVG image SVG image examplekernel-figure及kernel-image指令支持DOT格式文件Graphviz 的图描述语言。一个简单示例.. kernel-figure:: hello.dot :alt: hello world DOTs hello world example仓库中提供了这两个示例素材文件Documentation/doc-guide/svg_image.svg一个用 SVG 绘制的简单示意图与 Documentation/doc-guide/hello.dot内容为graph G { Hello -- World }。像 Graphviz 的DOT这类内嵌render标记或语言由kernel-render指令提供支持.. kernel-render:: DOT :alt: foobar digraph :caption: Embedded **DOT** (Graphviz) code digraph foo { bar - baz; }其渲染效果取决于已安装的工具若安装了 Graphviz将看到矢量图像否则原始标记会以literal-block字面代码块形式插入。render指令拥有figure指令的全部选项外加caption选项。若caption有值则插入figure节点否则插入image节点。若想对渲染结果建立引用也必须有caption。内嵌SVG的写法.. kernel-render:: SVG :caption: Embedded **SVG** markup :alt: so-nw-arrow ?xml version1.0 encodingUTF-8? svg xmlnshttp://www.w3.org/2000/svg version1.1 ... ... /svg以上三个指令kernel-image、kernel-figure、kernel-render全部由 Documentation/sphinx/kfigure.py 实现。从该扩展源码可以看出其设计意图从作者角度简化图像处理——kernel-figure等方法保证即使某些工具未安装也总能得到最佳输出格式核心转换逻辑集中在convert_image(...)函数中。其依赖的工具链包括dot(1)Graphviz渲染 DOT不可用时以 literal-block 插入 DOT 语言源码convert(1)ImageMagick或inkscape(1)Inkscape用于 SVG 转 PDFrsvg-convert(1)librsvg可用时用于 DOT 转 PDF。这正对应前文图像输出一节中要求安装 GraphViz 与 ImageMagick 的原因缺少这些工具时构建不会失败只是输出中不包含图像或退化为字面代码块。小结Linux 内核的文档体系以 reStructuredText 为源、以 Sphinx 为引擎、以 kernel-doc 为源码注释的桥梁。掌握make htmldocs/make pdfdocs/SPHINXDIRS等构建入口与 tools/docs/sphinx-pre-install 依赖检查工具即可在任何发行版上搭建可复现的文档构建环境遵循标题装饰顺序、表格语法、C Domain、路径式交叉引用与kernel-figure/kernel-render图像指令等社区约定则能写出与现有 Documentation 体系风格一致、可被自动索引与交叉引用的高质量内核文档。【免费下载链接】linuxLinux kernel source tree项目地址: https://gitcode.com/GitHub_Trending/li/linux创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考