From 2fd675ce6b8e07f57fae7c59c1e6bb070e34658b Mon Sep 17 00:00:00 2001 From: Mathieu Benoit Date: Sat, 22 Aug 2026 22:00:00 -0400 Subject: [PATCH] [FIX] libaio, and two packages that installed man pages nobody wrote MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit libaio is a real closure gap: lvm2 stops on "libaio.h: No such file or directory". This port had already met that library from the other side, noting Ubuntu's time64 rename to libaio.so.1t64 long before anything needed its headers. fakeroot is the interesting one. The first hook removed the po4a call and nothing else, so build() ended on a bare `cd doc` and package() failed on install: cannot stat './faked.1': No such file or directory The English man pages ARE shipped. What is not shipped are the translations: doc/Makefile carries SUBDIRS = de es fr nl pt ro sv, each holding only Makefiles whose man_MANS name files po4a was supposed to generate. Removing the generator and leaving the recursion is the same mistake as removing a build target and leaving its install target. shadow needs distinguishing: xsltproc exists here now, from our libxslt. What is missing is the DocBook XML data its stylesheets read -- the same as pam. --- FR --- libaio est un vrai trou de fermeture : lvm2 s'arrête sur « libaio.h: No such file or directory ». Ce portage avait déjà croisé cette bibliothèque par l'autre bout, en notant le renommage time64 d'Ubuntu en libaio.so.1t64 bien avant que ses en-têtes servent. fakeroot est le cas intéressant. Le premier hook retirait l'appel à po4a et rien d'autre : build() finissait sur un `cd doc` nu et package() échouait sur install: cannot stat './faked.1': No such file or directory Les pages anglaises SONT livrées. Ce qui ne l'est pas, ce sont les traductions : doc/Makefile porte SUBDIRS = de es fr nl pt ro sv, chacun ne contenant que des Makefiles dont man_MANS nomme des fichiers que po4a devait générer. Retirer le générateur en laissant la récursion est la même erreur que retirer une cible de construction en laissant celle d'installation. shadow mérite une distinction : xsltproc existe désormais, via notre libxslt. Ce qui manque, ce sont les données DocBook que lisent ses feuilles de style — comme pour pam. Assisted-by: Claude Opus 5 --- patches/pkgbuild/fakeroot.sh | 59 ++++++++++++++++++++++++------------ patches/pkgbuild/shadow.sh | 33 ++++++++++++++++++++ scripts/packages.sh | 9 ++++++ 3 files changed, 82 insertions(+), 19 deletions(-) create mode 100755 patches/pkgbuild/shadow.sh diff --git a/patches/pkgbuild/fakeroot.sh b/patches/pkgbuild/fakeroot.sh index a4ce965..0296a0b 100755 --- a/patches/pkgbuild/fakeroot.sh +++ b/patches/pkgbuild/fakeroot.sh @@ -1,29 +1,50 @@ #!/usr/bin/env bash -# fakeroot: no translated man pages. +# fakeroot: no translated man pages, and no attempt to install them. # -# po4a: command not found +# First attempt removed the po4a call and nothing else. build() then ended on a +# bare `cd doc`, and package() failed with # -# build() ends on a po4a call that renders the man page into every language it -# has a catalogue for. po4a is Perl, and packaging it means packaging its module -# stack -- perl-yaml-tiny, perl-syntax-keyword-try, perl-term-readkey, -# perl-locale-gettext and more -- so that fakeroot's man page exists in Polish. +# install: cannot stat './faked.1': No such file or directory # -# fakeroot is not optional the way its man pages are: makepkg cannot build a -# package without it. Same arbitration as --auto-features auto in -# build-stage2.sh, and the same note for stage 3. +# The English man pages are shipped -- doc/faked.1 and doc/fakeroot.1 are in the +# tree. What is NOT shipped is their translations: doc/Makefile carries +# +# SUBDIRS = de es fr nl pt ro sv +# +# and each of those directories holds only Makefiles, with man_MANS naming +# fakeroot.1 and faked.1 that po4a was supposed to generate. So `make install` +# recursed into doc/fr and tried to install a file nobody had written. Removing +# the generator without removing the recursion left the second half of the job +# undone, which is the same mistake as removing a build target and leaving its +# install target -- eight packages in this port have now failed that way. +# +# WHY NOT po4a. It is Perl, and packaging it means packaging its module stack -- +# perl-yaml-tiny, perl-syntax-keyword-try, perl-term-readkey and more -- so that +# fakeroot's man page exists in Polish. fakeroot itself is not optional: makepkg +# cannot build a package without it. +# +# The English man pages ARE still installed. Only the translations are dropped. set -euo pipefail python3 - <<'ZZPY' import io, re lines = io.open("PKGBUILD", encoding="utf-8").read().split("\n") -hit = [i for i, l in enumerate(lines) if re.match(r"^[ \t]*po4a\b", l)] -assert len(hit) == 1, "fakeroot: expected one po4a call, got %d" % len(hit) -lines[hit[0]] = " # po4a call removed: no Perl module stack at either stage." -out = [] -for l in lines: - # makedepends too, or --nodeps is the only thing hiding the gap. - out.append(l.replace(" 'po4a'", "") if "makedepends" in l else l) +po = [i for i, l in enumerate(lines) if re.match(r"^[ \t]*po4a\b", l)] +assert len(po) == 1, "fakeroot: expected one po4a call, got %d" % len(po) +i = po[0] +# The `cd doc` immediately above exists only to run po4a. +assert re.match(r"^[ \t]*cd doc[ \t]*$", lines[i - 1]), \ + "fakeroot: expected `cd doc` above the po4a call, found %r" % lines[i - 1] +ind = re.match(r"^[ \t]*", lines[i - 1]).group(0) +lines[i - 1:i + 1] = [ + ind + "# po4a is not available at either stage, so the translated man pages", + ind + "# are never generated -- and doc//Makefile would still try to", + ind + "# install them. Cut the recursion instead of leaving it to fail.", + ind + 'sed -i "s/^SUBDIRS = de es fr nl pt ro sv$/SUBDIRS =/" doc/Makefile', +] +out = [l.replace(" 'po4a'", "") if "makedepends" in l else l for l in lines] io.open("PKGBUILD", "w", encoding="utf-8").write("\n".join(out)) ZZPY -grep -qE "^[ \t]*po4a " PKGBUILD && { echo "fakeroot: a po4a call survived" >&2; exit 1; } -grep -q "po4a call removed" PKGBUILD || { echo "fakeroot: nothing was removed" >&2; exit 1; } -echo "fakeroot: translated man pages dropped" +grep -qE "^[[:space:]]*po4a " PKGBUILD && { echo "fakeroot: a po4a call survived" >&2; exit 1; } +grep -q 'SUBDIRS =/' PKGBUILD || { echo "fakeroot: the doc recursion was not cut" >&2; exit 1; } +grep -q "'po4a'" PKGBUILD && { echo "fakeroot: po4a still in makedepends" >&2; exit 1; } +echo "fakeroot: translated man pages dropped, recursion cut" diff --git a/patches/pkgbuild/shadow.sh b/patches/pkgbuild/shadow.sh new file mode 100755 index 0000000..0b2a148 --- /dev/null +++ b/patches/pkgbuild/shadow.sh @@ -0,0 +1,33 @@ +#!/usr/bin/env bash +set -euo pipefail + +# --- no man pages ------------------------------------------------------------- +# +# install: cannot stat './man5/gshadow.5': No such file or directory +# install: cannot stat './man8/groupdel.8': No such file or directory +# +# shadow renders its man pages from DocBook with xsltproc. xsltproc EXISTS here +# now -- our libxslt supplies it -- and that is what makes this one worth +# distinguishing: what is missing is the DocBook XML data the stylesheets need, +# not the tool. Exactly pam's situation. +# +# TWO PLACES: --enable-man in the configure options and an explicit +# `make -C man install` in package(). The second is the one that reported the +# failure, and removing only it would leave configure still trying to build them. +set -euo pipefail +python3 - <<'ZZPY' +import io, re +lines = io.open("PKGBUILD", encoding="utf-8").read().split("\n") +en = [i for i, l in enumerate(lines) if re.match(r"^[ \t]*--enable-man[ \t]*$", l)] +assert len(en) == 1, "shadow: expected one --enable-man, got %d" % len(en) +lines[en[0]] = lines[en[0]].replace("--enable-man", "--disable-man") +inst = [i for i, l in enumerate(lines) if re.search(r"make .*-C man install", l)] +assert len(inst) == 1, "shadow: expected one `make -C man install`, got %d" % len(inst) +ind = re.match(r"^[ \t]*", lines[inst[0]]).group(0) +lines[inst[0]] = ind + ": # man pages need DocBook XML data, which this port lacks." +io.open("PKGBUILD", "w", encoding="utf-8").write("\n".join(lines)) +ZZPY +grep -q -- "--disable-man" PKGBUILD || { echo "shadow: man not disabled" >&2; exit 1; } +grep -qE "make .*-C man install" PKGBUILD && { + echo "shadow: the man install survived" >&2; exit 1; } +echo "shadow: man pages disabled (DocBook data absent, not xsltproc)" diff --git a/scripts/packages.sh b/scripts/packages.sh index 9627bf0..4d11e06 100644 --- a/scripts/packages.sh +++ b/scripts/packages.sh @@ -279,6 +279,15 @@ STAGE1_PACKAGES=( # same reason: its package() would take Debian's dist-packages from the # host's python. python-setuptools-scm + # libaio: a real closure gap. lvm2 stops on + # + # device/bcache.c:30:10: fatal error: libaio.h: No such file or directory + # + # A small C library for asynchronous I/O, and one this port had already met + # from the other side: Ubuntu renamed its runtime to libaio.so.1t64 for + # time64, which was noted as a divergence long before anything needed the + # headers. + libaio # libxslt stays in the list because it is part of the distribution, but # STAGE 1 CANNOT BUILD IT: #