]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
do not install manpages for unbuilt binaries
authorAydın Mercan <aydin@isc.org>
Tue, 24 Jun 2025 13:30:15 +0000 (16:30 +0300)
committerAydın Mercan <aydin@isc.org>
Mon, 30 Jun 2025 08:58:13 +0000 (11:58 +0300)
Building and installing from a git release installed all manpages
unconditionally even if binaries like dnstap-read were disabled and not
built.

Now the manpage configuration checks for such cases and also cleans up
remaining artifacts and unnecessary pages if the build directory is
reconfigured.

doc/man/README.md [new file with mode: 0644]
doc/man/conf.py
meson.build
util/meson-dist-package.sh

diff --git a/doc/man/README.md b/doc/man/README.md
new file mode 100644 (file)
index 0000000..2814b3e
--- /dev/null
@@ -0,0 +1,41 @@
+<!--
+Copyright (C) Internet Systems Consortium, Inc. ("ISC")
+
+SPDX-License-Identifier: MPL-2.0
+
+This Source Code Form is subject to the terms of the Mozilla Public
+License, v. 2.0.  If a copy of the MPL was not distributed with this
+file, you can obtain one at https://mozilla.org/MPL/2.0/.
+
+See the COPYRIGHT file distributed with this work for additional
+information regarding copyright ownership.
+-->
+# Building the Manpage
+
+## Building from the tarball
+
+When building BIND from the tarball, there will be pre-generated `.in` manpage templates.
+For every page relevant to the build (`man_srcset`), meson will generate the manpage and install it using `install_man`.
+
+Sphinx can also be used like in git tree builds described below but the pages generated with sphinx will not be installed if templated ones are available.
+
+## Building from the git tree
+
+Sphinx is required when building the manpages from the git tree.
+If `sphinx-build` didn't exist when creating the build directory, build targets for the manpage will not exist.
+Use the command `meson configure --clearcache` to force the next build to probe for sphinx again.
+
+The source set `manrst_srcset` is used only to determine when a rebuild is necessary from meson's perspective and doesn't actually pass the source files.
+Sphinx works by handling entire directories and so meson needs to use `depend_files` for the task.
+
+To find which optional manpages need to be built or not, we pass the build directory to sphinx using the environment variable `BIND_BUILD_ROOT`.
+Sphinx will then inspect the meson-generated `intro-targets.json` file to see which optional build components are enabled.
+
+If an optional component like LMDB is disabled in the build directory, its corresponding manpage needs to be removed.
+From meson's perspective, the entire folder is the output and doesn't concern itself with the insides specifically.
+This is done by checking which optional targets are not built but have the page entry in the output folder.
+
+If the `BIND_BUILD_ROOT` is not specified, sphinx will build every page.
+This is used when creating a release tarball.
+Meson will use the script `util/meson-dist-package.sh` to create the templates when runnnig the `dist` command.
+If sphinx is not available in the build directory, this step will be skipped and so the tarballs must be created on a system with `sphinx-build`.
index 2ba58b805e4714562c0e22df3c3d6b3e44c379dc..d0d8f65843714cfcf4366bafe0d2a1ae2b69c9f8 100644 (file)
@@ -11,6 +11,8 @@
 # information regarding copyright ownership.
 ############################################################################
 
+import json
+import os
 import sys
 
 from pathlib import Path
@@ -123,13 +125,6 @@ man_pages = [
     ),
     ("dnssec-signzone", "dnssec-signzone", "DNSSEC zone signing tool", author, 1),
     ("dnssec-verify", "dnssec-verify", "DNSSEC zone verification tool", author, 1),
-    (
-        "dnstap-read",
-        "dnstap-read",
-        "print dnstap data in human-readable form",
-        author,
-        1,
-    ),
     (
         "filter-aaaa",
         "filter-aaaa",
@@ -181,13 +176,6 @@ man_pages = [
         author,
         1,
     ),
-    (
-        "named-nzd2nzf",
-        "named-nzd2nzf",
-        "convert an NZD database to NZF text format",
-        author,
-        1,
-    ),
     (
         "named-rrchecker",
         "named-rrchecker",
@@ -206,6 +194,53 @@ man_pages = [
     ("tsig-keygen", "tsig-keygen", "TSIG key generation tool", author, 8),
 ]
 
+bind_optional_pages = {
+    "dnstap-read": (
+        "dnstap-read",
+        "dnstap-read",
+        "print dnstap data in human-readable form",
+        author,
+        1,
+    ),
+    "named-nzd2nzf": (
+        "named-nzd2nzf",
+        "named-nzd2nzf",
+        "convert an NZD database to NZF text format",
+        author,
+        1,
+    ),
+}
+
+bind_build_root = os.getenv("BIND_BUILD_ROOT")
+if bind_build_root is None:
+    man_pages.extend(bind_optional_pages.values())
+else:
+    bind_build_path = Path(bind_build_root).resolve()
+    with open(
+        bind_build_path / "meson-info" / "intro-targets.json", encoding="utf-8"
+    ) as f:
+        for target in json.load(f):
+            if target["name"] in bind_optional_pages:
+                page = bind_optional_pages.pop(target["name"])
+                man_pages.append(page)
+
+    # Delete artifacts if an optional binary is no longer built.
+    # This happens when the build directory is reconfigured to exclude
+    # dnstap etc.
+    #
+    # Meson can't handle this because:
+    # - "man.p" is under our control
+    # - Meson just expects an entire folder as an output, this is just how sphinx works.
+    for unused in bind_optional_pages.values():
+        doctree = bind_build_path / "man.p" / f"{unused[0]}.doctree"
+        if doctree.exists():
+            doctree.unlink()
+
+        page = bind_build_path / "man" / f"man{unused[4]}" / f"{unused[0]}.{unused[4]}"
+        if page.exists():
+            page.unlink()
+
+
 #
 # The rst_epilog will be completely overwritten from meson
 # the definition here is provided for when manpages are generated
index c00be2bdce3f19f963b7edd00d42188c8a3aae3c..6a1e57fa9a160c4c038a16512ce6aa3ac47433aa 100644 (file)
@@ -1670,6 +1670,7 @@ if doc_opt.allowed()
 
         custom_target(
             'man',
+            build_always_stale: true,
             depend_files: manrst_srcconf.sources(),
             depends: doc_misc_targets,
             install: man_srcconf.sources().length() == 0,
index 7a60e18c756011f3b5e3c1c091a6044ce4217715..3fb6e56c54f999c1545c98f1d6ff47d041346c38 100644 (file)
@@ -18,9 +18,6 @@ if [ -z "$MESON_DIST_ROOT" ] || [ -z "$MESON_SOURCE_ROOT" ]; then
   exit 1
 fi
 
-export BIND_BUILD_ROOT=${MESON_BUILD_ROOT}
-export BIND_SOURCE_ROOT=${MESON_SOURCE_ROOT}
-
 generate_man_pages() {
   export MESON_PROJECT_VERSION=$1