Subject: Re: bug#63789: Native compilation broken on the Hurd (with patch)

From: Ludovic Courtès <[email-masked]>
Date: Thu, 01 Jun 2023 23:50:13 +0200

Hello!

Janneke Nieuwenhuizen <[email-masked]> skribis:

> The commit
>
>     56759d30d9a817a9c9221c9468a4c4a59c9a4713
>     gnu: Switch to GCC 11.
>
> introduced a gratuitous dependency on coreutils-boot0 to gcc-boot0 by
> adding this atypical snippet
>
>         (snippet
>          #~(begin
>              ;; XXX: The GCC test suite contains files with non-ASCII file
>              ;; names, which cannot be repacked by BOOTSTRAP-ORIGIN.  Nor
>              ;; can it be deleted from Guile, so resort to this evil hack.
>              #$(origin-snippet (package-source gcc))
>              (system* #$(file-append coreutils-boot0 "/bin/rm") "-rf"
>                       "gcc/testsuite/go.test/test/fixedbugs/issue27836.dir"))))))
>
>
> This is problematic, because coreutils-boot0 doesn't build for the Hurd:
> coreutils needs hurd headers, and our hurd-headers-boot0 depends
> on...coreutils-boot0.
>
> Why was coreutils-boot0 used instead of the canonical
> delete-file-recursively?

That was my first reaction too :-), but it’s explained in the comment:
there are non-ASCII file names that Guile fails to decode (throwing a
decoding error at that point.)

Seeing is believing so I had to try:

--8<---------------cut here---------------start------------->8---
applying '/gnu/store/5705r4ajxl8lav1hz9xm19w75zdcz1n2-gcc-5.0-libvtv-runpath.patch'...
applying '/gnu/store/c2f49hzb4scsqaccfr8vf74f06z0yvp1-gcc-10-tree-sra-union-handling.patch'...
find-files: gcc-11.3.0/gcc/testsuite/go.test/test/fixedbugs/issue27836.dir/Äfoo.go: No such file or directory
Backtrace:
In srfi/srfi-1.scm:
 465: 19 [fold #<procedure 14397b0 at ice-9/ftw.scm:451:38 (subdir result+visited)> ...]
In ice-9/ftw.scm:
 452: 18 [#<procedure 14397b0 at ice-9/ftw.scm:451:38 (subdir result+visited)> # #]
 450: 17 [loop "gcc" "gcc-11.3.0" ...]
In srfi/srfi-1.scm:
 465: 16 [fold #<procedure 177df60 at ice-9/ftw.scm:451:38 (subdir result+visited)> ...]
In ice-9/ftw.scm:
 452: 15 [#<procedure 177df60 at ice-9/ftw.scm:451:38 (subdir result+visited)> # #]
 450: 14 [loop "testsuite" "gcc-11.3.0/gcc" ...]
In srfi/srfi-1.scm:
 465: 13 [fold #<procedure 20374e0 at ice-9/ftw.scm:451:38 (subdir result+visited)> ...]
In ice-9/ftw.scm:
 452: 12 [#<procedure 20374e0 at ice-9/ftw.scm:451:38 (subdir result+visited)> # #]
 450: 11 [loop "go.test" "gcc-11.3.0/gcc/testsuite" ...]
In srfi/srfi-1.scm:
 465: 10 [fold #<procedure 27d6a80 at ice-9/ftw.scm:451:38 (subdir result+visited)> ...]
In ice-9/ftw.scm:
 452: 9 [#<procedure 27d6a80 at ice-9/ftw.scm:451:38 (subdir result+visited)> # #]
 450: 8 [loop "test" "gcc-11.3.0/gcc/testsuite/go.test" ...]
In srfi/srfi-1.scm:
 465: 7 [fold #<procedure 208d060 at ice-9/ftw.scm:451:38 (subdir result+visited)> ...]
In ice-9/ftw.scm:
 452: 6 [#<procedure 208d060 at ice-9/ftw.scm:451:38 (subdir result+visited)> # #]
 450: 5 [loop "fixedbugs" "gcc-11.3.0/gcc/testsuite/go.test/test" ...]
In srfi/srfi-1.scm:
 465: 4 [fold #<procedure 1a92e40 at ice-9/ftw.scm:451:38 (subdir result+visited)> ...]
In ice-9/ftw.scm:
 452: 3 [#<procedure 1a92e40 at ice-9/ftw.scm:451:38 (subdir result+visited)> # #]
 474: 2 [loop "issue27836.dir" ...]
In guix/build/utils.scm:
 559: 1 [#<procedure dc3320 at guix/build/utils.scm:555:28 (file stat errno result)> "gcc-11.3.0/gcc/testsuite/go.test/test/fixedbugs/issue27836.dir/Äfoo.go" ...]
In unknown file:
   ?: 0 [scm-error misc-error #f "~A" ("find-files failed") #f]

ERROR: In procedure scm-error:
ERROR: find-files failed
builder for `/gnu/store/p2wypjic1f26w2gk6dihn3inzfv426i4-gcc-11.3.0.tar.xz.drv' failed with exit code 1
--8<---------------cut here---------------end--------------->8---

When decoded as UTF-8, those file names look like this:

--8<---------------cut here---------------start------------->8---
$ export LC_ALL=en_US.UTF-8
$ tar tvf $(guix build "/gnu/store/pfc1094f3vdc74a6pls7b54m949y5gff-gcc-11.3.0.tar.xz.drv") |grep issue27836
-rw-r--r-- rguenther/users     191 2022-04-21 07:58 gcc-11.3.0/gcc/testsuite/go.test/test/fixedbugs/issue27836.go
drwxr-xr-x rguenther/users       0 2022-04-21 07:58 gcc-11.3.0/gcc/testsuite/go.test/test/fixedbugs/issue27836.dir/
-rw-r--r-- rguenther/users     192 2022-04-21 07:58 gcc-11.3.0/gcc/testsuite/go.test/test/fixedbugs/issue27836.dir/Äfoo.go
-rw-r--r-- rguenther/users     203 2022-04-21 07:58 gcc-11.3.0/gcc/testsuite/go.test/test/fixedbugs/issue27836.dir/Ämain.go
--8<---------------cut here---------------end--------------->8---

> So, until we can correct the gcc-boot0 snippet problem in the next
> rebuild cycle (how does that work now that we don't have core-updates
> anymore?, I made coreutils-boot0 build on the Hurd.  See the patch
> below.

Re “how does that work?”, good question! :-)

We should get rid of that hack though.

>>>From 37f38eb35fff505da9bfad8cb1f5f250378f7648 Mon Sep 17 00:00:00 2001
> Message-Id: <[email-masked]>
> From: Janneke Nieuwenhuizen <[email-masked]>
> Date: Mon, 29 May 2023 10:34:42 +0200
> Subject: [PATCH] gnu: commencement: coreutils-boot0: Fix native build for the
>  Hurd.
>
> * gnu/packages/patches/coreutils-boot0-hurd_types.patch: New file.
> * gnu/local.mk (dist_patch_DATA): Add it.
> * gnu/packages/commencement.scm (coreutils-boot0)[arguments]: When building
> for the hurd, add new phase 'add-hurd_types.h' and use it.  Add
> "ac_cv_member_struct_stat_st_author=no" and -Wl,-rpath for %bootstrap-libc to
> configure flags when building for the Hurd.  Add make-flags with
> "IGNORE_UNUSED_LIBRARIES_CFLAGS=" to avoid -Wl,--as-needed, which undoes
> previous rpath option.
> ---
>  gnu/local.mk                                  |  1 +
>  gnu/packages/commencement.scm                 | 56 +++++++++----
>  .../patches/coreutils-boot0-hurd_types.patch  | 82 +++++++++++++++++++
>  3 files changed, 122 insertions(+), 17 deletions(-)
>  create mode 100644 gnu/packages/patches/coreutils-boot0-hurd_types.patch

Neat!  This is probably okay but I wonder if we can either shrink this
patch or use a different strategy.

I tried a few things; I thought we could get ‘coreutils-boot0’ to build
nothing but ‘rm’ (since the build failure the patch above works around
is in ‘src/copy.c’), but my attempt below doesn’t work: it insists on
building other things, including ‘src/copy.c’.  I ran out of time but I
think it should be possible to make it work.

Even better would have been ‘--enable-no-install-program=cp’ but
‘src/copy.c’ is still getting built.

(Time passes…)

Just as I was about to give up, I looked at:

  guix graph -e '(@@ (gnu packages commencement) guile-final)' -s i586-gnu -M3 |xdot -

and found the solution:

diff --git a/gnu/packages/commencement.scm b/gnu/packages/commencement.scm
index 78cfa4acd0..de3728ae26 100644
--- a/gnu/packages/commencement.scm
+++ b/gnu/packages/commencement.scm
@@ -2333,7 +2333,13 @@ (define gcc-boot0
              ;; names, which cannot be repacked by BOOTSTRAP-ORIGIN.  Nor
              ;; can it be deleted from Guile, so resort to this evil hack.
              #$(origin-snippet (package-source gcc))
-             (system* #$(file-append coreutils-boot0 "/bin/rm") "-rf"
+             (system* #$(file-append (let-system system
+                                       ;; Work around
+                                       ;; <https://issues.guix.gnu.org/63789>.
+                                       (if (target-hurd? system)
+                                           %bootstrap-coreutils&co
+                                           coreutils-boot0))
+                                     "/bin/rm") "-rf"
                       "gcc/testsuite/go.test/test/fixedbugs/issue27836.dir"))))))
     (arguments
      (cons*

How does that sound? :-)

Ludo’.

diff --git a/gnu/packages/commencement.scm b/gnu/packages/commencement.scm
index 78cfa4acd0..17745705f7 100644
--- a/gnu/packages/commencement.scm
+++ b/gnu/packages/commencement.scm
@@ -1997,24 +1997,41 @@ (define coreutils-boot0
      `(("make" ,gnu-make-boot0)
        ,@(%bootstrap-inputs+toolchain)))
     (arguments
-     `(#:tests? #f
-       #:implicit-inputs? #f
-       #:guile ,%bootstrap-guile
-       ,@(package-arguments coreutils)
-       ;; The %bootstrap-glibc for aarch64 and armhf doesn't have
-       ;; $output/include/linux/prctl.h which causes some binaries
-       ;; to fail to build with coreutils-9.0+.
-       ,@(if (target-arm?)
-           `(#:configure-flags '(,(string-append
-                                    "--enable-no-install-program="
-                                    ;; the defaults to not install.
-                                    "arch,coreutils,hostname"
-                                    ;; fails due to missing headers.
-                                    ",timeout,sort")
-                                  ,@(if (target-arm32?)
-                                      `("--disable-year2038")
-                                      `())))
-           '())))))
+     (substitute-keyword-arguments (package-arguments coreutils)
+       ((#:tests? _ #t)
+        #f)
+       ((#:implicit-inputs? _ #t)
+        #f)
+       ((#:guile _ #f)
+        %bootstrap-guile)
+       ((#:configure-flags flags ''())
+        ;; The %bootstrap-glibc for aarch64 and armhf doesn't have
+        ;; $output/include/linux/prctl.h which causes some binaries
+        ;; to fail to build with coreutils-9.0+.
+        (if (target-arm?)
+            `'(,(string-append "--enable-no-install-program="
+                               ;; the defaults to not install.
+                               "arch,coreutils,hostname"
+                               ;; fails due to missing headers.
+                               ",timeout,sort")
+               ,@(if (target-arm32?)
+                     `("--disable-year2038")
+                     `()))
+            ''()))
+       ((#:phases phases '%standard-phases)
+        (if (target-hurd?)
+            `(modify-phases ,phases
+               (add-after 'unpack 'build-nothing-but-rm
+                 ;; XXX: Normally we wouldn't depend on coreutils-boot0 for
+                 ;; GNU/Hurd; unfortunately, it is used for the gcc-boot0
+                 ;; snippet below.  Since the snippet needs nothing but 'rm',
+                 ;; build just that (thus avoiding build errors in other
+                 ;; programs).
+                 (lambda _
+                   (substitute* "Makefile.in"
+                     (("^bin_PROGRAMS = .*")
+                      "bin_PROGRAMS = src/rm\n")))))
+            phases))))))
 
 (define diffutils-boot0
   (package
diff --git a/guix/packages.scm b/guix/packages.scm
index e26602d589..0802d863b1 100644
--- a/guix/packages.scm
+++ b/guix/packages.scm
@@ -944,6 +944,13 @@ (define* (patch-and-repack source patches
         (locales (lookup-input "locales"))
         (comp    (and=> (compressor source-file-name) lookup-input))
         (patches (map instantiate-patch patches)))
+    (define fail-on-error?
+      #t
+      #;(let-system (system target)
+        (pk 'fail? system (->bool (or locales
+                               target
+                               (not (string-prefix? "-gnu" system)))))))
+
     (define build
       (with-imported-modules '((guix build utils))
         #~(begin
@@ -986,7 +993,7 @@ (define* (patch-and-repack source patches
                                 (format port "~a~%" name))
                               (find-files directory
                                           #:directories? #t
-                                          #:fail-on-error? #t)))))
+                                          #:fail-on-error? #$fail-on-error?)))))
 
               (apply invoke #+(file-append tar "/bin/tar")
                      "cvfa" output