Subject: [PATCH v2]: Correct some inputs / native-inputs issues with guile

From: Maxime Devos <[email-masked]>
Date: Sat, 20 Mar 2021 22:45:47 +0100

Hi Guix,

The first patch ‘gnu: Explicitely pass the guile binary to wrap-script.’
does what it say what it does.  This is important for picking up the guile
binary for the architecture in --target instead of the guile from native-inputs.

(The unpatched & patched package definitions do not have a guile native-input,
so before this patch they wouldn't pick up a guile at all -- packages in inputs
do not contribute to the $PATH when cross-compiling.)

The second patch ‘gnu: Make guile packages cross-compilable when the fix is trivial.’
only touches guile libraries.  It adds guile to the native-inputs when required,
sometimes it adds guile to inputs and sometimes it copies propagated-inputs & inputs
to native-inputs when cross-compiling.  It also fixes some other cross-compilations
issues like autoconf being in inputs instead of native-inputs.

The second patch only touches gnu/packages/guile-xyz.scm; other packages are ignored.
Also ignored are: emacsy-minimal (there have been patches and/or bug reports lately)
guile-bash (retired project) and guile-studio (it is an Emacs package).

Suggested testing method:

(start shell script)
# BAD_PACKAGES: fails to compile
BAD_PACKAGES="guile2.0-commonmark guile3.0-ncurses-with-gpm guile-dbi guile2.2-pfds"

# OK_PACKAGES: compiles & cross-compiles
OK_PACKAGES="guildhall guile-daemon guile-dsv guile-filesystem guile2.0-filesystem guile2.2-filesystem guile-syntax-highlight guile2.2-
syntax-highlight guile-sjson guile-sparql guile-email guile-mastodon guile-parted guile2.2-parted guile-config guile-hall guile-wisp
guile-commonmark guile-stis-parser guile-persist guile-file-names guile-srfi-158 guile-semver jupyter-guile-kernel guile-ics srfi-64-
driver guile-websocket g-wrap guile-webutils guile-srfi-159 guile-torrent guile-irc guile-machine-code guile2.2-sjson guile2.2-dsv
guile2.2-email guile2.2-config guile2.2-hall guile2.2-ics guile2.2-wisp guile2.2-commonmark guile2.2-semver guile2.2-webutils guile-redis
guile2.2-redis guile2.0-redis guile-irregex guile2.0-irregex guile2.2-irregex mcron guile2.2-mcron guile-srfi-89 guile-srfi-145 guile-
srfi-180 guile-jpeg guile-hashing guile2.2-hashing guile-packrat guile-ac-d-bus guile-lens guile2.2-lens guile-rdf guile-jsonld guile-
struct-pack guile-laesare guile-mkdir-p guile-jwt guile-r6rs-protobuf guile-shapefile schmutz guile-cbor guile-8sync guile-squee guile2.2-
squee guile-colorized guile2.2-colorized guile-pfds guile-prometheus guile-aa-tree guile-simple-zmq guile2.2-simple-zmq guile-debbugs
guile-email-latest guile-miniadapton guile-lib guile2.0-lib guile2.2-lib guile-minikanren guile2.0-minikanren guile2.2-minikanren python-
on-guile"

# NOT_CROSS_COMPILABLE: self-describing (compiles natively)
NOT_CROSS_COMPILABLE="guile-cv guile-gi guile-ncurses g-golf guile-picture-language guile-sly guile-aspell guile-fibers guile-sodium
guile-reader guile-udev haunt guile2.2-haunt guile2.0-haunt guile2.2-ncurses guile-ncurses-with-gpm guile-xosd artanis guile-xapian
guile2.2-xapian guile-newt guile2.2-newt guile2.2-reader guile-avahi guile2.0-pg guile-libyaml guile-eris guile-ffi-fftw "

make
# replace aarch64 with architecture of choice and maybe adjust -M and -c
./pre-inst-env guix build $OK_PACKAGES $NOT_CROSS_COMPILABLE -M6 -c1 --fallback
./pre-inst-env guix build $OK_PACKAGES -M6 -c1 --target=aarch64-linux-gnu --fallback
make as-derivation
(end shell script)

Greetings,
Maxime
From 039d1526600971e90a3ff5183ee7a2fe3055af5b Mon Sep 17 00:00:00 2001
From: Maxime Devos <[email-masked]>
Date: Thu, 18 Mar 2021 14:40:20 +0100
Subject: [PATCH 1/2] gnu: Explicitely pass the guile binary to wrap-script.

If the #:guile argument of wrap-script is not set,
then a guile binary will be searched for in the PATH.

When cross-compiling, this would result in a guile package
compiled for a wrong architecture being used (if guile is in
native-inputs) or a broken wrapper script that tries to use
"#f" as interpreter.

Note that there are more cross-compilation issues
lurking in the affected packages, e.g. gess uses a
python of the incorrect architecture.

Partially fixes: <https://issues.guix.gnu.org/47221>.

* gnu/packages/xdisorg.scm (clipmenu)[arguments]: Use the
  guile of the target platform in wrap-script.
* gnu/packages/vpn.scm (vpnc-scripts)[arguments]: Likewise.
* gnu/packages/mail.scm (sieve-connect)[arguments]: Likewise.
* gnu/packages/bioinformatics.scm
  (proteinortho)[arguments]: Likewise.
  (prinseq)[arguments]: Likewise.
  (gess)[arguments]: Likewise.
  (nanopolish)[arguments]: Likewise.
---
 gnu/packages/bioinformatics.scm | 29 ++++++++++++++++++++---------
 gnu/packages/mail.scm           |  4 +++-
 gnu/packages/vpn.scm            |  2 ++
 gnu/packages/xdisorg.scm        |  4 +++-
 4 files changed, 28 insertions(+), 11 deletions(-)

diff --git a/gnu/packages/bioinformatics.scm b/gnu/packages/bioinformatics.scm
index eb466868d1..d62a6f8643 100644
--- a/gnu/packages/bioinformatics.scm
+++ b/gnu/packages/bioinformatics.scm
@@ -5432,10 +5432,13 @@ predicts the locations of structural units in the sequences.")
              #t))
          (add-after 'install 'wrap-programs
            (lambda* (#:key inputs outputs #:allow-other-keys)
-             (let ((path (getenv "PATH"))
-                   (out (assoc-ref outputs "out")))
+             (let* ((path (getenv "PATH"))
+                    (out (assoc-ref outputs "out"))
+                    (guile (assoc-ref inputs "guile")))
                (for-each (lambda (script)
-                           (wrap-script script `("PATH" ":" prefix (,path))))
+                           (wrap-script script
+                             #:guile (string-append guile "/bin/guile")
+                             `("PATH" ":" prefix (,path))))
                          (cons (string-append out "/bin/proteinortho")
                                (find-files out "\\.(pl|py)$"))))
              #t)))))
@@ -7523,13 +7526,16 @@ experience substantial biological insertions and deletions.")
          (delete 'configure)
          (delete 'build)
          (replace 'install
-           (lambda* (#:key outputs #:allow-other-keys)
+           (lambda* (#:key inputs outputs #:allow-other-keys)
              (let* ((out (assoc-ref outputs "out"))
-                    (bin (string-append out "/bin")))
+                    (bin (string-append out "/bin"))
+                    (guile (assoc-ref inputs "guile"))
+                    (guile-binary (string-append guile "/bin/guile")))
                (for-each (lambda (file)
                            (chmod file #o555)
                            (install-file file bin)
                            (wrap-script (string-append bin "/" (basename file))
+                                        #:guile guile-binary
                                         `("PERL5LIB" ":" prefix
                                           (,(getenv "PERL5LIB")))))
                          (find-files "." "prinseq.*.pl"))))))))
@@ -10468,7 +10474,8 @@ remove biased methylation positions for RRBS sequence files.")
                              out "/lib/python"
                              ,(version-major+minor
                                 (package-version python))
-                             "/site-packages/gess/")))
+                             "/site-packages/gess/"))
+                    (guile (assoc-ref inputs "guile")))
                (mkdir-p target)
                (copy-recursively "." target)
                ;; Make GESS.py executable
@@ -10483,6 +10490,7 @@ matplotlib.use('Agg')
 " line)))
                ;; Make sure GESS has all modules in its path
                (wrap-script (string-append target "GESS.py")
+                 #:guile (string-append guile "/bin/guile")
                  `("PYTHONPATH" ":" = (,target ,(getenv "PYTHONPATH"))))
                (mkdir-p bin)
                (symlink (string-append target "GESS.py")
@@ -13831,16 +13839,19 @@ choosing which reads pass the filter.")
                            (find-files "scripts" ".*"))
                  #t)))
            (add-after 'install 'wrap-programs
-             (lambda* (#:key outputs #:allow-other-keys)
+             (lambda* (#:key inputs outputs #:allow-other-keys)
                (let ((pythonpath (getenv "PYTHONPATH"))
                      (perl5lib (getenv "PERL5LIB"))
                      (scripts (string-append (assoc-ref outputs "out")
-                                             "/share/nanopolish/scripts")))
+                                             "/share/nanopolish/scripts"))
+                     (guile (assoc-ref inputs "guile")))
                  (for-each (lambda (file)
                              (wrap-program file `("PYTHONPATH" ":" prefix (,pythonpath))))
                            (find-files scripts "\\.py"))
                  (for-each (lambda (file)
-                             (wrap-script file `("PERL5LIB" ":" prefix (,perl5lib))))
+                             (wrap-script file
+                               #:guile (string-append guile "/bin/guile")
+                               `("PERL5LIB" ":" prefix (,perl5lib))))
                            (find-files scripts "\\.pl"))))))))
       (inputs
        `(("guile" ,guile-3.0) ; for wrappers
diff --git a/gnu/packages/mail.scm b/gnu/packages/mail.scm
index 239ddb0eb0..95850d9586 100644
--- a/gnu/packages/mail.scm
+++ b/gnu/packages/mail.scm
@@ -2842,8 +2842,10 @@ transfer protocols.")
          (add-after 'install 'wrap-program
            (lambda* (#:key inputs outputs #:allow-other-keys)
              (let ((out (assoc-ref outputs "out"))
-                   (path (getenv "PERL5LIB")))
+                   (path (getenv "PERL5LIB"))
+                   (guile (assoc-ref inputs "guile")))
                (wrap-script (string-append out "/bin/sieve-connect")
+                 #:guile (string-append guile "/bin/guile")
                  `("PERL5LIB" ":" = (,path)))
                #t))))))
     (inputs
diff --git a/gnu/packages/vpn.scm b/gnu/packages/vpn.scm
index 2ea04acaa2..ece7a3f7ad 100644
--- a/gnu/packages/vpn.scm
+++ b/gnu/packages/vpn.scm
@@ -196,6 +196,8 @@ Only \"Universal TUN/TAP device driver support\" is needed in the kernel.")
                  (for-each
                   (lambda (script)
                     (wrap-script (string-append out "/etc/vpnc/" script)
+                      #:guile (string-append (assoc-ref inputs "guile")
+                                             "/bin/guile")
                       `("PATH" ":" prefix
                         ,(map (lambda (name)
                                 (let ((input (assoc-ref inputs name)))
diff --git a/gnu/packages/xdisorg.scm b/gnu/packages/xdisorg.scm
index 56ac53edec..5aad1c8cce 100644
--- a/gnu/packages/xdisorg.scm
+++ b/gnu/packages/xdisorg.scm
@@ -2545,10 +2545,12 @@ tools to complement clipnotify.")
                       (gawk              (assoc-ref inputs "gawk"))
                       (util-linux        (assoc-ref inputs "util-linux"))
                       (xdotool           (assoc-ref inputs "xdotool"))
-                      (xsel              (assoc-ref inputs "xsel")))
+                      (xsel              (assoc-ref inputs "xsel"))
+                      (guile             (assoc-ref inputs "guile")))
                  (for-each
                   (lambda (prog)
                     (wrap-script (string-append out "/bin/" prog)
+                      #:guile (string-append guile "/bin/guile")
                       `("PATH" ":" prefix
                         ,(map (lambda (dir)
                                 (string-append dir "/bin"))
-- 
2.31.0

From 600a07d218211a7eb4cd4648cb6775f73526b982 Mon Sep 17 00:00:00 2001
From: Maxime Devos <[email-masked]>
Date: Thu, 18 Mar 2021 22:27:24 +0100
Subject: [PATCH 2/2] gnu: Make guile packages cross-compilable when the fix is
 trivial.
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Often, all that has to be done is adding guile to the native-inputs.
Sometimes upstream does not pass --target=host to "guild compile";
this is not addressed by this patch (but a comment has been added
to affected packages for future reference).  Sometimes libraries
from propagated-inputs have to be copied to native-inputs when
cross-compiling for unknown reasons.

Some packages (e.g. guile-sodium) have dependencies that cannot
be cross-compiled.  In this case, guile is still added to the
native-inputs but fixing the dependency is left for a later
patch.

Some definitions of guile packages outside gnu/packages/guile-xyz.scm
probably need to be adjusted as well,  but I have run out of stream.

Partially fixes: <https://issues.guix.gnu.org/47221>.

* gnu/packages/guile-xyz.scm
  (artanis)[native-inputs]: Add the guile package and a
  comment noting the makefile forgets to pass the target
  architecture to "guild compile" with --target.
  (guildhall)[native-inputs]: Likewise.
  (guile-daemon)[native-inputs]: Likewise.
  (guile-filesystem)[native-inputs]: Likewise.
  (guile-syntax-highlight)[native-inputs]: Likewise.
  (guile-sjson)[native-inputs]: Likewise.
  (guile-sparql)[native-inputs]: Likewise.
  (guile-email)[native-inputs]: Likewise.
  (guile-config)[native-inputs]: Likewise.
  (guile-sly)[native-inputs]: Likewise.
  (g-golf)[native-inputs]: Likewise.
  (haunt)[native-inputs]: Likewise.
  (guile-commonmark)[native-inputs]: Likewise.
  (guile-picture-language)[native-inputs]: Likewise.
  (guile-stis-parser)[native-inputs]: Likewise.
  (guile-persist)[native-inputs]: Likewise.
  (guile-file-names)[native-inputs]: Likewise.
  (guile-gi)[native-inputs]: Likewise.
  (guile-srfi-158)[native-inputs]: Likewise.
  (guile-semver)[native-inputs]: Likewise.
  (guile-xapian)[native-inputs]: Likewise.
  (guile-syntax-highlight)[native-inputs]: Likewise.
  (jupyter-guile-kernel)[native-inputs]: Add the guile package.
  (guile-dbi)[native-inputs]: Likewise.
  (guile-reader)[native-inputs]: Likewise.
  (srfi-64-driver)[native-inputs]: Likewise.
  (guile-websocket)[native-inputs]: Likewise.
  (guile-xosd)[native-inputs]: Likewise.
  (guile-lens)[inputs]: Add the guile package.
  (guile-debbugs)[inputs]: Likewise.
  (guile-8sync)[inputs]: Likewise.
  (guile-jpeg)[inputs]: Add guile-2.2.
  (guile-newt)[native-inputs]: Add guile, note that --target
  is not set and note a cross-compilation error.
  (guile-parted)[native-inputs]: Add guile, note that --target
  is not set, and add guile-bytestructures when cross-compiling.
  (guile-hall)[native-inputs]: Add guile, and add
  guile-config when cross-compiling.
  (guile-debbugs)[native-inputs]: Add guile-email
  when cross-compiling.
  (guile-ac-d-bus)[native-inputs]: Add guile-packrat
  when cross-compiling.
  (python-on-guile)[native-inputs]: Add guile and add
  guile-persist, guile-readline and guile-stis when
  cross-compiling.
  (guile-srfi-180)[native-inputs]: Add guile-srfi-145
  when cross-compiling.
  (python-on-guile)[arguments]: Note that the interpreter
  is wrapped incorrectly when cross-compiling.
  (guile-udev)[native-inputs]: Add guile and note that
  package still fails to cross-compile.
  (guile-wisp)[native-inputs]: Add guile, and do not include
  emacs when cross-compiling.
  (guile-wisp)[arguments]: Do not compile emacs lisp code
  when cross-compiling and tell the configure script where
  to find python when cross-compiling.
  (guile-simple-zmq)[native-inputs,inputs]: Move autoconf,
  automake and pkg-config to native-inputs and add guile
  to inputs.
  (guile-ics)[native-inputs,inputs]: Add the guile package to
  native-inputs and move which from inputs to native-inputs.
  Also add guile-lib to native-inputs when cross-compiling
  (guile-redis)[native-inputs]: Add the guile package to inputs
  and note that --target is not yet passed to "guild compile".
  (guile-mastodon)[native-inputs]: Add the guile package to native-inputs,
  and add guile-json-4 as well when cross-compiling.
  (guile-dsv)[native-inputs]: Add the guile package to native-inputs
  and add guile-lib as well when cross-compiling.
  (guile-fibers)[native-inputs]: Add the guile package to native-inputs,
  note that --target is not yet passed to "guild compile" and note the
  build still fails when cross-compiling.
  (guile-cv)[native-inputs,propagated-inputs]: Add guile-2.2 to
  native-inputs and use the guile-2.2 variant of guile-lib in
  propagated-inputs instead of the guile-3.0 invariant.
  (guile-ncurses)[native-inputs]: Add guile to native inputs, and
  note that it still fails to cross-compile.
  (guile-aspell)[native-inputs]: Not that a guile package *not*
  being required here is rather unusual.
  (g-wrap)[native-inputs]: Add the guile package, which will
  only be used for ./configure.
  (guile-webutils)[native-inputs]: Add the guile package, and add
  the propagated inputs when cross-compiling.
  (guile-srfi-159)[inputs,native-inputs]: Move guile from
  inputs to native-inputs.
  (guile-ffi-fftw)[arguments,inputs,native-inputs]: Add a comment
  notice the ‘check’ build phase is broken when cross-compiling
  and move guile from inputs to native-inputs.
  (guile-torrent)[inputs,native-inputs]: Add guile to both
  inputs and native-inputs, note that --target is not
  passed to "guild compile" and add guile-gcrypt to native-inputs
  when cross-compiling.
  (guile-irc)[native-inputs]: Add guile and GnuTLS to native-inputs.
  The latter is required by the configure script.
  (guile-rdf)[native-inputs]: Add guile to native-inputs,  noting
  --target is not passed to "guild compile".  Also add guile-json,
  guile-gnutls and guile-rdf which are required for unknown reasons.
  (guile-machine-code)[native-inputs]: Add guile-struct-pack to
  native-inputs, which is required for unknown reasons.
  (guile-sodium)[native-inputs]: Add guile, and note that this
  package still fails to cross-compile.
  (guile3.0-ncurses/gpm): Note this fails to compile natively.
  (guile2.0-pg): Note this fails to cross-compile.
  (guile2.2-sjson)[native-inputs]: Add guile-2.2 to native-inputs.
  (guile2.2-dsv)[native-inputs]: Likewise.
  (guile2.2-email)[native-inputs]: Likewise.
  (guile2.2-newt)[native-inputs]: Likewise.
  (guile2.2-config)[native-inputs]: Likewise.
  (guile2.2-wisp)[native-inputs]: Likewise.
  (guile2.2-ncurses)[native-inputs]: Likewise.
  (guile2.2-haunt)[native-inputs]: Likewise.
  (guile2.2-commonmark)[native-inputs]: Likewise.
  (guile2.2-semver)[native-inputs]: Likewise.
  (guile2.2-xapian)[native-inputs]: Likewise.
  (guile2.2-reader)[native-inputs]: Likewise.
  (guile2.2-filesystem)[native-inputs]: Likewise
  (guile2.2-syntax-highlight)[native-inputs]: Likewise
  (guile-ncurses/gpm)[native-inputs]: Likewise.
  (guile2.2-parted)[native-inputs]: Use guile-2.2
  and guile2.2-bytestructures instead of the -3.0
  versions.
  (guile2.2-hall)[native-inputs]: Likewise with guile2.2-config.
  (guile2.0-haunt)[native-inputs]: Add guile-2.0 to native-inputs.
  (guile2.0-filesystem)[native-inputs]: Likewise.
  (guile2.0-commonmark)[native-inputs]: Likewise, and note this
  package fails to compile natively.
  (guile2.2-redis)[inputs]: Replace guile-3.0 with guile-2.2 in
  the inputs.
  (guile2.0-redis)[inputs]: Likewise with guile-2.0.
  (guile2.2-simple-zmq)[native-inputs]:  Add pkg-config, autoconf and
  automake.
  (guile2.2-simple-zmq)[inputs]: Use guile-2.2 instead.
  (guile2.2-webutils)[native-inputs]: Add guile-2.2 to native-inputs
  and use the guile-2.2 variants of guile libraries.
  (guile2.2-ics)[native-inputs]: Add guile-2.2 to native-inputs
  and add guile2.2-lib when cross-compiling..
---
 gnu/packages/guile-xyz.scm | 488 +++++++++++++++++++++++++++++++------
 1 file changed, 407 insertions(+), 81 deletions(-)

diff --git a/gnu/packages/guile-xyz.scm b/gnu/packages/guile-xyz.scm
index d89b9954de..0342fe74c8 100644
--- a/gnu/packages/guile-xyz.scm
+++ b/gnu/packages/guile-xyz.scm
@@ -35,6 +35,7 @@
 ;;; Copyright © 2020, 2021 pukkamustard <[email-masked]>
 ;;; Copyright © 2021 Bonface Munyoki Kilyungi <[email-masked]>
 ;;; Copyright © 2021 Xinglu Chen <[email-masked]>
+;;; Copyright © 2021 Maxime Devos <[email-masked]>
 ;;;
 ;;; This file is part of GNU Guix.
 ;;;
@@ -175,6 +176,7 @@
        ("guile-redis" ,guile2.2-redis)))
     (native-inputs
      `(("bash"       ,bash)         ;for the `source' builtin
+       ("guile"      ,guile-2.2)    ;for `guild compile' (TODO --target is not set)
        ("pkgconfig"  ,pkg-config)
        ("util-linux" ,util-linux))) ;for the `script' command
     (arguments
@@ -301,6 +303,7 @@ AM_SCM_LOG_FLAGS =  --no-auto-compile -s")
        `(("guile" ,guile-2.0)))
       (native-inputs
        `(("zip" ,zip) ; for tests
+         ("guile" ,guile-2.0) ; for guile-tools compile (TODO --target is not set)
          ("autoconf" ,autoconf)
          ("automake" ,automake)
          ("texinfo" ,texinfo)))
@@ -349,7 +352,10 @@ $(datadir)/guile/site/$(GUILE_EFFECTIVE_VERSION)\n"))
                            (string-append "\"" aspell
                                           "/lib/libaspell\"")))
                         #t))))))
-    (native-inputs `(("pkg-config" ,pkg-config)))
+    (native-inputs `(("pkg-config" ,pkg-config)
+                     ;; If guile-aspell compiled its source code,
+                     ;; a "guile" native-input would be required.
+                     ))
     (inputs `(("guile" ,guile-2.2)
               ("aspell" ,aspell)))
     (home-page "https://github.com/spk121/guile-aspell")
@@ -445,6 +451,8 @@ and then run @command{scm example.scm}.")
                      ("guile" ,guile-2.2)
                      ("pkg-config" ,pkg-config)
                      ("texinfo" ,texinfo)))
+    ;; Required for cross-compilation.
+    (inputs `(("guile" ,guile-2.2)))
     (arguments
      `(#:phases (modify-phases %standard-phases
                   (add-before 'configure 'setenv
@@ -476,7 +484,8 @@ Note that 8sync is only available for Guile 2.2.")
                 "08gaqrgjlly9k5si72vvpbr4xhq5v52l5ma5y6a7spid5dd057cy"))))
     (build-system gnu-build-system)
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
+     `(("guile" ,guile-2.2) ; for "guild compile" (TODO --target is not set)
+       ("pkg-config" ,pkg-config)))
     (inputs
      `(("guile" ,guile-2.2)))
     (home-page "https://github.com/alezost/guile-daemon")
@@ -505,7 +514,13 @@ you send to a FIFO file.")
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
        ("pkg-config" ,pkg-config)
-       ("texinfo" ,texinfo)))
+       ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)
+       ;; TODO this should not be necessary
+       ,@(if (%current-target-system)
+             `(("guile-lib" ,guile-lib))
+             '())))
     (inputs `(("guile" ,guile-3.0)))
     (propagated-inputs `(("guile-lib" ,guile-lib)))
     (arguments
@@ -560,10 +575,21 @@ Unix-style DSV format and RFC 4180 format.")
   (package
     (inherit guile-dsv)
     (name "guile2.2-dsv")
+    (native-inputs
+     `(("guile" ,guile-2.2)
+       ,@(if (%current-target-system)
+             `(("guile-lib" ,guile2.2-lib))
+             '())
+       ,@(alist-delete '("guile" "guile-lib")
+                       (package-native-inputs guile-dsv)
+                       (lambda (x y) (member y x)))))
     (inputs `(("guile" ,guile-2.2)))
     (propagated-inputs `(("guile-lib" ,guile2.2-lib)))))
 
 (define-public guile-fibers
+  ;; This fails to cross-compile:
+  ;; ‘In procedure dynamic-mink: "/tmp/guix-build-.../.libs/epoll",
+  ;; message: "file not found"
   (package
     (name "guile-fibers")
     (version "1.0.0")
@@ -618,7 +644,9 @@ Unix-style DSV format and RFC 4180 format.")
                         #t))))))
     (native-inputs
      `(("texinfo" ,texinfo)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)))
     (inputs
      `(("guile" ,guile-3.0)))
     (synopsis "Lightweight concurrency facility for Guile")
@@ -663,7 +691,9 @@ is not available for Guile 2.0.")
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
        ("pkg-config" ,pkg-config)
-       ("texinfo" ,texinfo)))
+       ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO: --target is missing)
+       ("guile" ,guile-3.0)))
     (inputs
      `(("guile" ,guile-3.0)))
     (home-page "https://gitlab.com/leoprikler/guile-filesystem")
@@ -676,12 +706,18 @@ that augment Guile's support for handling files and their names.")
   (package
     (inherit guile-filesystem)
     (name "guile2.0-filesystem")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.0)
+                    (package-native-inputs guile-filesystem)))
     (inputs `(("guile" ,guile-2.0)))))
 
 (define-public guile2.2-filesystem
   (package
     (inherit guile-filesystem)
     (name "guile2.2-filesystem")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-filesystem)))
     (inputs `(("guile" ,guile-2.2)))))
 
 (define-public guile-syntax-highlight
@@ -707,7 +743,9 @@ that augment Guile's support for handling files and their names.")
                   #t))))
     (build-system gnu-build-system)
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
+     `(("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)))
     (inputs
      `(("guile" ,guile-3.0)))
     (synopsis "General-purpose syntax highlighter for GNU Guile")
@@ -722,6 +760,9 @@ HTML (via SXML) or any other format for rendering.")
   (package
     (inherit guile-syntax-highlight)
     (name "guile2.2-syntax-highlight")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-syntax-highlight)))
     (inputs `(("guile" ,guile-2.2)))))
 
 (define-public guile3.0-syntax-highlight
@@ -750,7 +791,9 @@ HTML (via SXML) or any other format for rendering.")
     (native-inputs
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)))
     (inputs
      `(("guile" ,guile-3.0)))
     (home-page "https://gitlab.com/dustyweb/guile-sjson")
@@ -763,6 +806,9 @@ It has a nice, simple s-expression based syntax.")
   (package
     (inherit guile-sjson)
     (name "guile2.2-sjson")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-sjson)))
     (inputs `(("guile" ,guile-2.2)))))
 
 (define-public guile-squee
@@ -910,6 +956,9 @@ Vicare Scheme and IronScheme.  Right now it contains:
     (license license:bsd-3)))
 
 (define-public guile2.0-pg
+  ;; TODO: this fails to cross-compile as the guile library
+  ;; in native-inputs is linked against instead of the library
+  ;; in inputs.
   (package
     (name "guile2.0-pg")
     (version "0.49")
@@ -1048,11 +1097,12 @@ convenient nested tree operations.")
          '("GUILE_AUTO_COMPILE=0"))) ;to prevent guild warnings
 
       (native-inputs
-       `(("guile" ,guile-3.0)))
-      (inputs
-       `(("autoconf" ,autoconf)
+       `(("guile" ,guile-3.0)
+         ("autoconf" ,autoconf)
          ("automake" ,automake)
-         ("pkg-config" ,pkg-config)
+         ("pkg-config" ,pkg-config)))
+      (inputs
+       `(("guile" ,guile-3.0)
          ("zeromq" ,zeromq)))
       (home-page "https://github.com/jerry40/guile-simple-zmq")
       (synopsis "Guile wrapper over ZeroMQ library")
@@ -1065,7 +1115,10 @@ messaging library.")
   (package
     (inherit guile-simple-zmq)
     (name "guile2.2-simple-zmq")
-    (native-inputs `(("guile" ,guile-2.2)))))
+    (inputs (alist-replace "guile" (list guile-2.2)
+                           (package-inputs guile-simple-zmq)))
+    (native-inputs (alist-replace "guile" (list guile-2.2)
+                                  (package-native-inputs guile-simple-zmq)))))
 
 (define-public guile3.0-simple-zmq
   (deprecated-package "guile3.0-simple-zmq" guile-simple-zmq))
@@ -1148,6 +1201,13 @@ messaging library.")
                                                            'prefix)
                                               ", \"-s"))))
                           #t))))))
+      (native-inputs
+       ;; for cross-compilation
+       `(("guile" ,guile-3.0)
+         ,@(if (%current-target-system)
+               `(("guile-json" ,guile-json-3)
+                 ("guile-simple-zmq" ,guile-simple-zmq))
+               '())))
       (inputs
        `(("openssl" ,openssl)
          ("guile" ,guile-3.0)
@@ -1173,7 +1233,9 @@ allows users to interact with the Guile REPL through Jupyter.")
              (base32 "1jf4972f9fpm0rd865xpnc9mzl3xv6vhfnp0iygadydy905z9nln"))))
    (build-system gnu-build-system)
    (native-inputs
-    `(("pkg-config" ,pkg-config)))
+    `(("pkg-config" ,pkg-config)
+      ;; for "guild compile" (TODO --target is not set)
+      ("guile" ,guile-3.0)))
    (inputs
     `(("guile" ,guile-3.0)))
    (home-page "https://github.com/roelj/guile-sparql")
@@ -1199,7 +1261,13 @@ using S-expressions.")
      `(("guile-email" ,guile-email)))
     (native-inputs
      `(("guile" ,guile-3.0)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ,@(if (%current-target-system)
+             (package-propagated-inputs this-package)
+             '())))
+    (inputs
+     ;; Required for cross-compilation.
+     `(("guile" ,guile-3.0)))
     (home-page "https://savannah.gnu.org/projects/guile-debbugs/")
     (synopsis "Guile interface to the Debbugs bug tracking service")
     (description
@@ -1223,7 +1291,9 @@ tracker's SOAP service, such as @url{https://bugs.gnu.org}.")
     (build-system gnu-build-system)
     (native-inputs
      `(("pkg-config" ,pkg-config)
-       ("lzip" ,lzip)))
+       ("lzip" ,lzip)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)))
     (inputs
      `(("guile" ,guile-3.0)))
     (arguments
@@ -1257,12 +1327,16 @@ format.")
        `(("pkg-config" ,pkg-config)
          ("autoconf" ,autoconf)
          ("automake" ,automake)
-         ("texinfo" ,texinfo))))))
+         ("texinfo" ,texinfo)
+         ("guile" ,guile-3.0))))))
 
 (define-public guile2.2-email
   (package
     (inherit guile-email)
     (name "guile2.2-email")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-email)))
     (inputs `(("guile" ,guile-2.2)
               ,@(alist-delete "guile" (package-inputs guile-email))))))
 
@@ -1270,6 +1344,9 @@ format.")
   (deprecated-package "guile3.0-email" guile-email))
 
 (define-public guile-newt
+  ;; TODO: this fails to cross-compile:
+  ;; ‘In procedure dynamic-link: file: "[...]/lib/libnewt",
+  ;; message: "file not found"’
   (package
     (name "guile-newt")
     (version "0.0.2")
@@ -1292,7 +1369,9 @@ format.")
     (native-inputs
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO: --target is not set)
+       ("guile" ,guile-3.0)))
     (synopsis "Guile bindings to Newt")
     (description
      "This package provides bindings for Newt, a programming library for
@@ -1305,6 +1384,9 @@ Scheme by using Guile’s foreign function interface.")
   (package
     (inherit guile-newt)
     (name "guile2.2-newt")
+    (native-inputs
+     `(("guile" ,guile-2.2)
+       ,@(alist-delete "guile" (package-native-inputs guile-newt))))
     (inputs `(("guile" ,guile-2.2)
               ,@(alist-delete "guile" (package-inputs guile-newt))))))
 
@@ -1339,7 +1421,13 @@ Scheme by using Guile’s foreign function interface.")
        ("automake" ,automake)
        ("emacs" ,emacs-minimal)
        ("pkg-config" ,pkg-config)
-       ("texinfo" ,texinfo)))
+       ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO: --target is not set)
+       ("guile" ,guile-3.0)
+       ;; TODO this should not be required
+       ,@(if (%current-target-system)
+             `(("guile-json" ,guile-json-4))
+             '())))
     (inputs
      `(("guile" ,guile-3.0)
        ("gnutls" ,gnutls)
@@ -1377,7 +1465,13 @@ microblogging service.")
     (native-inputs
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)
+       ;; TODO this shouldn't be necessary
+       ,@(if (%current-target-system)
+             `(("guile-bytestructures" ,guile-bytestructures))
+             '())))
     (synopsis "Guile bindings to GNU Parted")
     (description
      "This package provides bindings for GNU Parted library, a C library
@@ -1390,6 +1484,14 @@ written in pure Scheme by using Guile's foreign function interface.")
   (package
     (inherit guile-parted)
     (name "guile2.2-parted")
+    (native-inputs
+     `(("guile" ,guile-2.2)
+       ,@(if (%current-target-system)
+             `(("guile-bytestructures" ,guile2.2-bytestructures))
+             '())
+       ,@(alist-delete '("guile" "guile-bytestructures")
+                       (package-native-inputs guile-parted)
+                       (lambda (x y) (member y x)))))
     (inputs `(("guile" ,guile-2.2)
               ,@(alist-delete "guile" (package-inputs guile-parted))))
     (propagated-inputs
@@ -1412,7 +1514,9 @@ written in pure Scheme by using Guile's foreign function interface.")
                 "1ri5065c16kmgrf2pysn2ymxjqi5302lhpb07wkl1jr75ym8fn8p"))))
     (build-system gnu-build-system)
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
+     `(("pkg-config" ,pkg-config)
+       ;; for "guild compile"
+       ("guile" ,guile-2.2)))
     (inputs
      `(("guile" ,guile-2.2)
        ("libx11" ,libx11)
@@ -1462,6 +1566,9 @@ library}.")
     (inputs
      `(("guile-dbd-sqlite3" ,guile-dbd-sqlite3)
        ("guile-dbd-postgresql" ,guile-dbd-postgresql))) ; only shared library, no scheme files
+    (native-inputs
+     ;; for "guild doc-snarf"
+     `(("guile" ,guile-2.2)))
     (propagated-inputs
      `(("guile" ,guile-2.2)))
     (synopsis "Guile database abstraction layer")
@@ -1582,7 +1689,9 @@ PostgreSQL.")
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
        ("pkg-config" ,pkg-config)
-       ("texinfo" ,texinfo)))
+       ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO: --target is not set)
+       ("guile" ,guile-3.0)))
     (inputs `(("guile" ,guile-3.0)))
     (synopsis
      "Guile application configuration parsing library.")
@@ -1602,6 +1711,9 @@ above command-line parameters.")
   (package
     (inherit guile-config)
     (name "guile2.2-config")
+    (native-inputs
+     `(("guile" ,guile-2.2)
+       ,@(alist-delete "guile" (package-native-inputs guile-config))))
     (inputs `(("guile" ,guile-2.2)
               ,@(alist-delete "guile" (package-inputs guile-config))))))
 
@@ -1673,7 +1785,13 @@ above command-line parameters.")
       `(("autoconf" ,autoconf)
         ("automake" ,automake)
         ("pkg-config" ,pkg-config)
-        ("texinfo" ,texinfo)))
+        ("texinfo" ,texinfo)
+        ;; for "guild compile" (TODO --target is not set)
+        ("guile" ,guile-3.0)
+        ;; TODO this shouldn't be necessary
+        ,@(if (%current-target-system)
+              (package-propagated-inputs this-package)
+              '())))
     (inputs `(("guile" ,guile-3.0)))
     (propagated-inputs
      `(("guile-config" ,guile-config)))
@@ -1692,6 +1810,14 @@ provides tight coupling to Guix.")
     (name "guile2.2-hall")
     (inputs `(("guile" ,guile-2.2)
               ,@(alist-delete "guile" (package-inputs guile-hall))))
+    (native-inputs
+     `(("guile" ,guile-2.2)
+       ,@(if (%current-target-system)
+             (package-propagated-inputs this-package)
+             '())
+       ,@(alist-delete '("guile" "guile-config")
+                       (package-native-inputs guile-hall)
+                       (lambda (x y) (member y x)))))
     (propagated-inputs
      `(("guile-config" ,guile2.2-config)
        ,@(alist-delete "guile-config"
@@ -1728,8 +1854,15 @@ provides tight coupling to Guix.")
        ("texinfo" ,texinfo)
        ;; Gettext brings 'AC_LIB_LINKFLAGS_FROM_LIBS'.
        ("gettext" ,gettext-minimal)
-       ("pkg-config" ,pkg-config)))
-    (inputs `(("guile" ,guile-3.0) ("which" ,which)))
+       ("pkg-config" ,pkg-config)
+       ("which" ,which)
+       ;; for "guild compile"
+       ("guile" ,guile-3.0)
+       ;; TODO this shouldn't be necessary
+       ,@(if (%current-target-system)
+             `(("guile-lib" ,guile-lib))
+             '())))
+    (inputs `(("guile" ,guile-3.0)))
     (propagated-inputs `(("guile-lib" ,guile-lib)))
     (home-page "https://github.com/artyom-poptsov/guile-ics")
     (synopsis "Guile parser library for the iCalendar format")
@@ -1746,6 +1879,13 @@ The library is shipped with documentation in Info format and usage examples.")
     (name "guile2.2-ics")
     (inputs `(("guile" ,guile-2.2)
               ,@(alist-delete "guile" (package-inputs guile-ics))))
+    (native-inputs
+     `(("guile" ,guile-2.2)
+       ,@(if (%current-target-system)
+             `(("guile-lib" ,guile2.2-lib))
+             '())
+       ,@(alist-delete '("guile" "guile-lib") (package-native-inputs guile-ics)
+                       (lambda (x y) (member y x)))))
     (propagated-inputs `(("guile-lib" ,guile2.2-lib)))))
 
 (define-public guile3.0-ics
@@ -1775,6 +1915,14 @@ The library is shipped with documentation in Info format and usage examples.")
        #:imported-modules (,@%gnu-build-system-modules
                            (guix build emacs-build-system)
                            (guix build emacs-utils))
+       ;; When cross-compiling, the configure script
+       ;; cannot find python by itself.
+       ,@(if (%current-target-system)
+             `(#:configure-flags
+               `(,(string-append "ac_cv_prog_python3="
+                                 (assoc-ref %build-inputs "python")
+                                 "/bin/python3")))
+             '())
        #:phases
        (modify-phases %standard-phases
          (replace 'bootstrap
@@ -1813,19 +1961,27 @@ The library is shipped with documentation in Info format and usage examples.")
                #t)))
          (add-after 'install 'install-emacs-files
            (assoc-ref emacs:%standard-phases 'install))
-         (add-after 'install-emacs-files 'compile-emacs-files
-           (assoc-ref emacs:%standard-phases 'build))
-         (add-after 'compile-emacs-files 'make-autoloads
-           (assoc-ref emacs:%standard-phases 'make-autoloads)))))
+         ;; TODO: the emacs build system currently does not
+         ;; support cross-compilation.
+         ,@(if (%current-target-system)
+               '()
+               '((add-after 'install-emacs-files 'compile-emacs-files
+                   (assoc-ref emacs:%standard-phases 'build))
+                 (add-after 'compile-emacs-files 'make-autoloads
+                   (assoc-ref emacs:%standard-phases 'make-autoloads)))))))
     (home-page "https://www.draketo.de/english/wisp")
     (inputs
      `(("guile" ,guile-3.0)))
     (native-inputs
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
-       ("emacs" ,emacs-minimal)
+       ("pkg-config" ,pkg-config)
+       ,@(if (%current-target-system)
+             '()
+             `(("emacs" ,emacs-minimal)))
        ("python" ,python)
-       ("pkg-config" ,pkg-config)))
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)))
     (synopsis "Whitespace to lisp syntax for Guile")
     (description "Wisp is a syntax for Guile which provides a Python-like
 whitespace-significant language.  It may be easier on the eyes for some
@@ -1836,12 +1992,18 @@ users and in some situations.")
   (package
     (inherit guile-wisp)
     (name "guile2.2-wisp")
+    (native-inputs
+     `(("guile" ,guile-2.2)
+       ,@(alist-delete "guile" (package-native-inputs guile-wisp))))
     (inputs `(("guile" ,guile-2.2)))))
 
 (define-public guile3.0-wisp
   (deprecated-package "guile3.0-wisp" guile-wisp))
 
 (define-public guile-udev
+  ;; TODO: this fails to cross-compile for aarch64-linux-gnu
+  ;; due to missing includes.  This has been fixed in master,
+  ;; but there is no new release yet.
   (package
     (name "guile-udev")
     (version "0.1.0")
@@ -1862,7 +2024,9 @@ users and in some situations.")
        ("libtool" ,libtool)
        ("texinfo" ,texinfo)
        ("pkg-config" ,pkg-config)
-       ("which" ,which)))
+       ("which" ,which)
+       ;; for "guild compile"
+       ("guile" ,guile-3.0)))
     (inputs
      `(("guile" ,guile-3.0)
        ("eudev" ,eudev)))
@@ -1909,7 +2073,9 @@ users and in some situations.")
              (string-append "--with-libgslcblas-prefix="
                             (assoc-ref %build-inputs "gsl")))))
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
+     `(("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-2.2)))
     (propagated-inputs
      `(("guile-sdl" ,guile-sdl)
        ("guile-opengl" ,guile-opengl)))
@@ -1948,7 +2114,9 @@ capabilities.")
          ("gettext" ,gettext-minimal)
          ("libtool" ,libtool)
          ("pkg-config" ,pkg-config)
-         ("xorg-server" ,xorg-server)))
+         ("xorg-server" ,xorg-server)
+         ;; for "guild compile" (TODO --target is not set)
+         ("guile" ,guile-2.2)))
       (inputs
        `(("guile" ,guile-2.2)
          ("guile-lib" ,guile2.2-lib)
@@ -2025,7 +2193,9 @@ object-oriented programming system, GOOPS.")
                 "0ak0bha37dfpj9kmyw1r8fj8nva639aw5xr66wr5gd3l1rqf5xhg"))))
     (build-system gnu-build-system)
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
+     `(("pkg-config" ,pkg-config)
+       ;; Not actually used, but ./configure requires a guile.
+       ("guile" ,guile-2.2)))
     (propagated-inputs
      `(("guile" ,guile-2.2)
        ("guile-lib" ,guile-lib)))
@@ -2082,6 +2252,9 @@ understand, extend, and port to host languages other than Scheme.")
       (license license:expat))))
 
 (define-public guile-reader
+  ;; TODO: this fails to cross-compile:
+  ;; ‘In procedure dynamic-link: file: "/tmp/.../src/libguile-reader",
+  ;; message: "file not found"
   (package
     (name "guile-reader")
     (version "0.6.3")
@@ -2094,7 +2267,9 @@ understand, extend, and port to host languages other than Scheme.")
                  "1fyjckmygkhq22lq8nqc86yl5zzbqd7a944dnz5c1f6vx92b9hiq"))))
     (build-system gnu-build-system)
     (native-inputs `(("pkgconfig" ,pkg-config)
-                     ("gperf" ,gperf)))
+                     ("gperf" ,gperf)
+                     ;; for "guild compile"
+                     ("guile" ,guile-3.0)))
     (inputs `(("guile" ,guile-3.0)))
     (synopsis "Framework for building readers for GNU Guile")
     (description
@@ -2116,9 +2291,15 @@ many readers as needed).")
   (package
     (inherit guile-reader)
     (name "guile2.2-reader")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-reader)))
     (inputs `(("guile" ,guile-2.2)))))
 
 (define-public guile-ncurses
+  ;; TODO this fails to cross-compile with
+  ;; ‘In procedure dynamic-link: file: "libguile-ncurses", message:
+  ;; "file not found"’.
   (package
     (name "guile-ncurses")
     (version "3.0")
@@ -2132,7 +2313,10 @@ many readers as needed).")
     (build-system gnu-build-system)
     (inputs `(("ncurses" ,ncurses)
               ("guile" ,guile-3.0)))
-    (native-inputs `(("pkg-config" ,pkg-config)))
+    (native-inputs
+     `(("pkg-config" ,pkg-config)
+       ;; for "guild compile"
+       ("guile" ,guile-3.0)))
     (arguments
      `(#:modules ((guix build gnu-build-system)
                   ((guix build guile-build-system)
@@ -2169,6 +2353,9 @@ library.")
   (package
     (inherit guile-ncurses)
     (name "guile2.2-ncurses")
+    (native-inputs
+     `(("pkg-config" ,pkg-config)
+       ("guile" ,guile-2.2)))
     (inputs `(("ncurses" ,ncurses)
               ("guile" ,guile-2.2)))))
 
@@ -2179,10 +2366,14 @@ library.")
   (package
     (inherit guile-ncurses)
     (name "guile-ncurses-with-gpm")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-ncurses)))
     (inputs `(("ncurses" ,ncurses/gpm)
               ("guile" ,guile-2.2)))))
 
 (define-public guile3.0-ncurses/gpm
+  ;; TODO: this fails to compile with (FAIL: menu_gc_refcount.scm)
   (package
     (inherit guile3.0-ncurses)
     (name "guile3.0-ncurses-with-gpm")
@@ -2449,7 +2640,9 @@ inspired by the SCSH regular expression system.")
                              #t)))))))))
     (native-inputs
      `(("pkg-config" ,pkg-config)
-       ("texinfo" ,texinfo)))
+       ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0-latest)))
     (inputs
      ;; Depend on the latest Guile to avoid bytecode compatibility issues when
      ;; using modules built against the latest version.
@@ -2469,6 +2662,9 @@ interface for reading articles in any format.")
     (inherit haunt)
     (name "guile2.2-haunt")
     (inputs `(("guile" ,guile-2.2)))
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs haunt)))
     (propagated-inputs
      `(("guile-reader" ,guile2.2-reader)
        ("guile-commonmark" ,guile2.2-commonmark)))))
@@ -2477,6 +2673,9 @@ interface for reading articles in any format.")
   (package
     (inherit haunt)
     (name "guile2.0-haunt")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.0)
+                    (package-native-inputs haunt)))
     (inputs `(("guile" ,guile-2.0)))))
 
 (define-public guile3.0-haunt
@@ -2499,10 +2698,14 @@ interface for reading articles in any format.")
     (build-system gnu-build-system)
     (arguments
      '(#:make-flags '("GUILE_AUTO_COMPILE=0")))
+    (inputs
+     ;; for cross-compilation
+     `(("guile" ,guile-3.0)))
     (native-inputs
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
        ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is missing)
        ("guile" ,guile-3.0)))
     (synopsis "Redis client library for Guile")
     (description "Guile-redis provides a Scheme interface to the Redis
@@ -2513,6 +2716,8 @@ key-value cache and store.")
   (package
     (inherit guile-redis)
     (name "guile2.2-redis")
+    (inputs (alist-replace "guile" (list guile-2.2)
+                           (package-inputs guile-redis)))
     (native-inputs `(("guile" ,guile-2.2)
                      ,@(alist-delete "guile"
                                      (package-native-inputs guile-redis))))))
@@ -2533,6 +2738,8 @@ key-value cache and store.")
                 "(rnrs io ports)"))
              #t)))
        ,@(package-arguments guile-redis)))
+    (inputs (alist-replace "guile" (list guile-2.0)
+                           (package-inputs guile-redis)))
     (native-inputs `(("guile" ,guile-2.0)
                      ,@(alist-delete "guile"
                                      (package-native-inputs guile-redis))))))
@@ -2574,7 +2781,9 @@ key-value cache and store.")
     (inputs
      `(("guile" ,guile-3.0)))
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
+     `(("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)))
     (synopsis "CommonMark parser for Guile")
     (description
      "guile-commonmark is a library for parsing CommonMark, a fully specified
@@ -2589,12 +2798,21 @@ is no support for parsing block and inline level HTML.")
   (package
     (inherit guile-commonmark)
     (name "guile2.2-commonmark")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-commonmark)))
     (inputs `(("guile" ,guile-2.2)))))
 
 (define-public guile2.0-commonmark
+  ;; TODO: this fails to compile (FAIL: tests/inlines/emphasis)
+  ;; The failing test is:
+  ;; ‘parse-inlines, emphasis with _ is not allowed inside words’
   (package
     (inherit guile-commonmark)
     (name "guile2.0-commonmark")
+    (native-inputs
+     (alist-replace "guile" (list guile-2.0)
+                    (package-native-inputs guile-commonmark)))
     (inputs `(("guile" ,guile-2.0)))))
 
 (define-public guile3.0-commonmark
@@ -2679,7 +2897,9 @@ format is also supported.")
          ("automake" ,automake)
          ("librsvg" ,librsvg)
          ("pkg-config" ,pkg-config)
-         ("texinfo" ,texinfo)))
+         ("texinfo" ,texinfo)
+         ;; for "guild compile" (TODO --target is not set)
+         ("guile" ,@(assoc-ref (package-inputs this-package) "guile"))))
       (home-page "https://git.elephly.net/software/guile-picture-language.git")
       (synopsis "Picture language for Guile")
       (description
@@ -2800,7 +3020,9 @@ completion, a simple mode line, etc.")
     (native-inputs
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,@(assoc-ref (package-inputs this-package) "guile"))))
     (home-page "https://gitlab.com/tampe/stis-parser")
     (synopsis "Parser combinator framework")
     (description
@@ -2850,7 +3072,9 @@ chunks can be expressions as well as simple tokens.")
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
        ("libtool" ,libtool)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,@(assoc-ref (package-inputs this-package) "guile"))))
     (home-page "https://gitlab.com/tampe/guile-persist")
     (synopsis "Persistence programming framework for Guile")
     (description
@@ -2907,6 +3131,7 @@ serializing continuations or delimited continuations.")
                     (compiled-path (string-append
                                     ccache ":"
                                     (getenv "GUILE_LOAD_COMPILED_PATH"))))
+               ;; TODO these load paths are incorrect when cross-compiling
                (wrap-program (string-append out "/bin/python")
                  `("GUILE_LOAD_PATH" ":" prefix
                    (,load-path))
@@ -2922,7 +3147,14 @@ serializing continuations or delimited continuations.")
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
        ("libtool" ,libtool)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,@(assoc-ref (package-inputs this-package) "guile"))
+       ,@(if (%current-target-system)
+             `(("guile-persist" ,guile-persist)
+               ("guile-readline" ,guile-readline)
+               ("guile-stis-parser" ,guile-stis-parser))
+             '())))
     (synopsis "Python implementation in Guile")
     (description
      "This package allows you to compile a Guile Python file to any target
@@ -2954,7 +3186,9 @@ from @code{tree-il}.")
     (inputs
      `(("guile" ,guile-2.2)))
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
+     `(("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,@(assoc-ref (package-inputs this-package) "guile"))))
     (home-page "https://gitlab.com/brandoninvergo/guile-file-names")
     (synopsis "Manipulate file names")
     (description
@@ -3017,7 +3251,9 @@ list of components.  This module takes care of that for you.")
        ("glib:bin" ,glib "bin") ; for glib-compile-resources
        ("libtool" ,libtool)
        ("pkg-config" ,pkg-config)
-       ("xorg-server" ,xorg-server)))
+       ("xorg-server" ,xorg-server)
+       ;; for "guild compile"
+       ("guile" ,@(assoc-ref (package-inputs this-package) "guile"))))
     (propagated-inputs
      `(("glib" ,glib)
        ("gobject-introspection" ,gobject-introspection)
@@ -3111,7 +3347,9 @@ denote the invalidity of certain code paths in a Scheme program.")
     (native-inputs
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,@(assoc-ref (package-inputs this-package) "guile"))))
     (inputs
      `(("guile" ,guile-3.0)))
     (home-page "https://gitlab.com/samplet/guile-srfi-158")
@@ -3143,7 +3381,7 @@ implementation in a thin Guile compatibility layer.")
        ;; The *-impl.scm files are actually included from module files; they
        ;; should not be compiled separately, but they must be installed.
        '(#:not-compiled-file-regexp "-impl\\.scm$"))
-      (inputs
+      (native-inputs
        `(("guile" ,guile-2.2)))
       (synopsis "Formatting combinators for Guile")
       (description
@@ -3181,7 +3419,10 @@ more expressive and flexible than the traditional @code{format} procedure.")
       (arguments
        '(#:not-compiled-file-regexp "body\\.scm$"))
       (native-inputs
-       `(("guile" ,guile-3.0)))
+       `(("guile" ,guile-3.0)
+         ,@(if (%current-target-system)
+               (package-propagated-inputs this-package)
+               '())))
       (propagated-inputs
        `(("guile-srfi-145" ,guile-srfi-145)))
       (home-page "https://srfi.schemers.org/srfi-180/")
@@ -3355,6 +3596,8 @@ in C using Gtk+-3 and WebKitGtk.")
          ("automake" ,automake)
          ("pkg-config" ,pkg-config)
          ("guile" ,guile-2.2)))
+      ;; For cross-compilation, to satisfy the configuration script.
+      (inputs `(("guile" ,guile-2.2)))
       (synopsis "JPEG file parsing library for Guile")
       (description
        "Guile-JPEG is a Scheme library to parse JPEG image files and to
@@ -3522,9 +3765,11 @@ feature-set, fully programmable in Guile Scheme.")
                                         texlive-standalone
                                         texlive-xcolor
                                         texlive-fonts-iwona)))
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,@(assoc-ref (package-inputs this-package) "guile"))))
     (propagated-inputs
-     `(("guile-lib" ,guile-lib)))
+     `(("guile-lib" ,guile2.2-lib)))
     (home-page "https://www.gnu.org/software/guile-cv/")
     (synopsis "Computer vision library for Guile")
     (description "Guile-CV is a Computer Vision functional programming library
@@ -3536,6 +3781,9 @@ clean and easy to use high level API.")
     (license license:gpl3+)))
 
 (define-public guile-ffi-fftw
+  ;; TODO This currently fails to cross-compile:
+  ;; ‘In procedure dynamic-link: file: "[...]/lib/libfftw3",
+  ;; message: "file not found"
   (let ((commit "294ad9e7491dcb40026d2fec9be2af05263be1c0")
         (revision "2"))
     (package
@@ -3561,13 +3809,13 @@ clean and easy to use high level API.")
                  (("\\(getenv \"GUILE_FFI_FFTW_LIBFFTW3_PATH\"\\)")
                   (format #f "\"~a/lib\"" (assoc-ref inputs "fftw"))))
                #t))
+           ;; TODO this cannot be done when cross-compiling
            (add-after 'build 'check
              (lambda _
                (invoke "guile" "-L" "mod"
                        "-s" "test/test-ffi-fftw.scm"))))))
-      (inputs
-       `(("fftw" ,fftw)
-         ("guile" ,guile-2.2)))
+      (inputs `(("fftw" ,fftw)))
+      (native-inputs `(("guile" ,guile-2.2)))
       (home-page "https://github.com/lloda/guile-ffi-fftw/")
       (synopsis "Access FFTW through Guile's FFI")
       (description "This is a minimal set of Guile FFI bindings for the FFTW
@@ -3595,7 +3843,8 @@ anything other than straight complex DFTs.")
        (modify-phases %standard-phases
          (delete 'build))))
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
+     `(("pkg-config" ,pkg-config)
+       ("guile" ,guile-2.2)))
     (inputs
      `(("guile" ,guile-2.2)))
     (home-page "https://ngyro.com/software/srfi-64-driver.html")
@@ -3618,9 +3867,10 @@ tests being run, resulting clearer and more specific output.")
                 "109p4n39ln44cxvwdccf9kgb96qx54makvd2ir521ssz6wchjyag"))))
     (build-system gnu-build-system)
     (native-inputs
-     `(("pkg-config" ,pkg-config)))
-    (inputs
-     `(("guile" ,guile-3.0)))
+     `(("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)))
+    (inputs `(("guile" ,guile-3.0)))
     (home-page "https://ngyro.com/software/guile-semver.html")
     (synopsis "Semantic Versioning (SemVer) for Guile")
     (description "This Guile library provides tools for reading,
@@ -3636,7 +3886,11 @@ the style of the Node Package Manager (NPM).")
     (inherit guile-semver)
     (name "guile2.2-semver")
     (inputs
-     `(("guile" ,guile-2.2)))))
+     (alist-replace "guile" (list guile-2.2)
+                    (package-inputs guile-semver)))
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-semver)))))
 
 (define-public guile-hashing
   (package
@@ -3786,7 +4040,10 @@ and space linear in the size of the input text.")
 
                       #t)))))
     (native-inputs
-     `(("guile" ,guile-3.0)))
+     `(("guile" ,guile-3.0)
+       ,@(if (%current-target-system)
+             (package-propagated-inputs this-package)
+             '())))
     (propagated-inputs
      `(("guile-packrat" ,guile-packrat)))
     (synopsis "D-Bus protocol implementation in R6RS Scheme")
@@ -3827,7 +4084,12 @@ gnome-keyring, and many more.")
        `(("autoconf" ,autoconf)
          ("automake" ,automake)
          ("pkg-config" ,pkg-config)
-         ("texinfo" ,texinfo)))
+         ("texinfo" ,texinfo)
+         ("guile" ,guile-3.0)
+         ;; TODO this shouldn't be necessary.
+         ,@(if (%current-target-system)
+               (package-propagated-inputs this-package)
+               '())))
       (inputs
        `(("guile" ,guile-3.0)))
       (propagated-inputs
@@ -3844,8 +4106,15 @@ as signed sessions, multipart message support, etc.")
   (package
     (inherit guile-webutils)
     (name "guile2.2-webutils")
-    (inputs
-     `(("guile" ,guile-2.2)))
+    (native-inputs
+     `(("guile" ,guile-2.2)
+       ,@(alist-delete '("guile" "guile-irregex" "guile-gcrypt")
+                       (package-native-inputs guile-webutils)
+                       (lambda (x y) (member y x)))
+       ,@(if (%current-target-system)
+             (package-propagated-inputs this-package)
+             '())))
+    (inputs `(("guile" ,guile-2.2)))
     (propagated-inputs
      `(("guile-irregex" ,guile2.2-irregex)
        ("guile-gcrypt" ,guile2.2-gcrypt)))))
@@ -3880,6 +4149,8 @@ as signed sessions, multipart message support, etc.")
          ("guile-hall" ,guile-hall)
          ("pkg-config" ,pkg-config)
          ("texinfo" ,texinfo)))
+      (inputs
+       `(("guile" ,guile-3.0)))
       (home-page "https://gitlab.com/a-sassmannshausen/guile-lens.git")
       (synopsis "Composable lenses for data structures in Guile")
       (description
@@ -3893,6 +4164,7 @@ over, or update a value in arbitrary data structures.")
   (package
     (inherit guile-lens)
     (name "guile2.2-lens")
+    (inputs `(("guile" ,guile-2.2)))
     (native-inputs
      `(("guile" ,guile-2.2)
        ,@(alist-delete "guile" (package-native-inputs guile-lens))))))
@@ -3924,7 +4196,9 @@ over, or update a value in arbitrary data structures.")
        ("automake" ,automake)
        ("libtool" ,libtool)
        ("pkg-config" ,pkg-config)
-       ("swig" ,swig)))
+       ("swig" ,swig)
+       ;; for "guild compile" (TODO --target is not set)
+       ("guile" ,guile-3.0)))
     (synopsis "Guile bindings for Xapian")
     (description "@code{guile-xapian} provides Guile bindings for Xapian, a
 search engine library.  Xapian is a highly adaptable toolkit which allows
@@ -3939,7 +4213,10 @@ models and also supports a rich set of boolean query operators.")
     (name "guile2.2-xapian")
     (inputs
      `(("guile" ,guile-2.2)
-       ,@(alist-delete "guile" (package-inputs guile-xapian))))))
+       ,@(alist-delete "guile" (package-inputs guile-xapian))))
+    (native-inputs
+     (alist-replace "guile" (list guile-2.2)
+                    (package-native-inputs guile-xapian)))))
 
 (define-public guile3.0-xapian
   (deprecated-package "guile3.0-xapian" guile-xapian))
@@ -3964,9 +4241,16 @@ models and also supports a rich set of boolean query operators.")
        ("guile" ,guile-2.2)
        ("texinfo" ,texinfo)
        ("perl" ,perl)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is missing)
+       ("guile" ,guile-2.2)
+       ,@(if (%current-target-system)
+             (package-propagated-inputs this-package)
+             '())))
     (propagated-inputs
-     `(("guile-gcrypt" ,guile-gcrypt)))
+     `(("guile-gcrypt" ,guile2.2-gcrypt)))
+    (inputs
+     `(("guile" ,guile-2.2)))
     (home-page "https://github.com/o-nly/torrent")
     (synopsis "Torrent library for GNU Guile")
     (description "This package provides facilities for working with
@@ -3995,7 +4279,11 @@ according to Bitorrent BEP003.")
       (native-inputs
        `(("autoconf" ,autoconf)
          ("automake" ,automake)
-         ("texinfo" ,texinfo)))
+         ("texinfo" ,texinfo)
+         ;; for "guild compile" (TODO --target is missing)
+         ("guile" ,guile-3.0)
+         ;; the configure script requires gnutls-cli
+         ("gnutls" ,gnutls)))
       (inputs
        `(("gnutls" ,gnutls)
          ("guile" ,guile-3.0)))
@@ -4042,7 +4330,9 @@ Relay Chat} (IRC).")
                #t)))))
       (native-inputs
        `(("autoconf" ,autoconf)
-         ("automake" ,automake)))
+         ("automake" ,automake)
+         ;; for "guild compile"
+         ("guile" ,guile-3.0)))
       (inputs
        `(("guile" ,guile-3.0)))
       (synopsis "Websocket server/client for Guile")
@@ -4077,7 +4367,9 @@ WebSocket protocol as defined by RFC 6455.")
      `(("automake" ,automake)
        ("autoconf" ,autoconf)
        ("pkg-config" ,pkg-config)
-       ("texinfo" ,texinfo)))
+       ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO --target is missing)
+       ("guile" ,guile-3.0)))
     (home-page "https://framagit.org/tyreunom/guile-rdf")
     (synopsis "Guile implementation of the RDF abstract and concrete syntaxes")
     (description "Guile RDF is an implementation of the RDF (Resource Description
@@ -4118,7 +4410,16 @@ manipulating graphs and datasets.")
      `(("automake" ,automake)
        ("autoconf" ,autoconf)
        ("pkg-config" ,pkg-config)
-       ("texinfo" ,texinfo)))
+       ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO --target is missing)
+       ("guile" ,guile-3.0)
+       ;; TODO this should not be necessary, but the configure
+       ;; script fails without it.
+       ,@(if (%current-target-system)
+             `(("guile-json" ,guile-json-4)
+               ("guile-gnutls" ,gnutls)
+               ("guile-rdf" ,guile-rdf))
+             '())))
     (home-page "https://framagit.org/tyreunom/guile-jsonld")
     (synopsis "Guile implementation of the JsonLD API specification")
     (description "Guile JsonLD is an implementation of the JsonLD (Json for
@@ -4208,7 +4509,12 @@ similar to struct in Python or pack and unpack in Perl.")
                                 files)
                       #t)))))
     (native-inputs
-     `(("guile" ,guile-3.0)))
+     `(("guile" ,guile-3.0)
+       ;; TODO this should not be necessary, but
+       ;; cross-compiling fails otherwise.
+       ,@(if (%current-target-system)
+             `(("guile-struct-pack" ,guile-struct-pack))
+             '())))
     (propagated-inputs
      `(("guile-struct-pack" ,guile-struct-pack)))
     (home-page "https://github.com/weinholt/machine-code")
@@ -4381,7 +4687,13 @@ directory of its argument if it does not exist.")
     (native-inputs
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
-       ("pkg-config" ,pkg-config)))
+       ("pkg-config" ,pkg-config)
+       ;; for "guild compile" (TODO --target is missing)
+       ("guile" ,guile-3.0)
+       ;; TODO this should not be necessary
+       ,@(if (%current-target-system)
+             `(("guile-json" ,guile-json-4))
+             '())))
     (propagated-inputs
      `(("guile-json" ,guile-json-4)))
     (inputs
@@ -4396,6 +4708,8 @@ JWT.  Supported algorithms: HS256, HS384, HS512.")
     (license license:gpl3+)))
 
 (define-public guile-sodium
+  ;; TODO this fails to cross-compile
+  ;; (‘In procedure dynamic-link: file: [...] not found’)
   (package
     (name "guile-sodium")
     (version "0.1.0")
@@ -4413,7 +4727,9 @@ JWT.  Supported algorithms: HS256, HS384, HS512.")
       `(("autoconf" ,autoconf)
         ("automake" ,automake)
         ("pkg-config" ,pkg-config)
-        ("texinfo" ,texinfo)))
+        ("texinfo" ,texinfo)
+        ;; for "guild compile" (TODO --target is missing)
+        ("guile" ,guile-3.0)))
     (inputs `(("guile" ,guile-3.0)))
     (propagated-inputs `(("libsodium" ,libsodium)))
     (synopsis "Guile bindings to the libsodium cryptographic library")
@@ -4443,6 +4759,8 @@ tools.")
        ("automake" ,automake)
        ("pkg-config" ,pkg-config)
        ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO --target is missing)
+       ("guile" ,guile-3.0)
        ;; test dependency
        ("guile-srfi-180" ,guile-srfi-180)))
     (inputs `(("guile" ,guile-3.0)))
@@ -4474,7 +4792,7 @@ read-capability.")
     (build-system guile-build-system)
     (arguments
      `(#:compile-flags '("--r6rs")))
-    (inputs
+    (native-inputs
      `(("guile" ,guile-3.0)))
     (home-page "https://gitlab.com/joolean/r6rs-protobuf/")
     (synopsis "Scheme implementation of Protocol Buffers")
@@ -4517,7 +4835,8 @@ including parsing and code generation.")
     (inputs
      `(("guile" ,guile-3.0)))
     (native-inputs
-     `(("texinfo" ,texinfo)))
+     `(("texinfo" ,texinfo)
+       ("guile" ,guile-3.0)))
     (home-page "https://github.com/HugoNikanor/guile-shapefile")
     (synopsis "Parse shapefiles in Guile")
     (description
@@ -4552,18 +4871,22 @@ including parsing and code generation.")
          (modify-phases %standard-phases
            (delete 'configure)
            (add-after 'unpack 'remove-unused-files
-             (lambda* (#:key inputs #:allow-other-keys)
+             (lambda* (#:key native-inputs inputs #:allow-other-keys)
                (for-each delete-file
                          '("guix.scm" "demo1.yml" "demo1.scm"
                            "yaml/libyaml.scm"
                            ;; This file is mismatched with the generated FFI code.
                            "yaml/ffi-help-rt.scm"))
-               (copy-file (string-append (assoc-ref inputs "nyacc")
+               ;; The file ffi-help-rt.scm is the same across architectures,
+               ;; so there's no need to add nyacc to the (non-native) inputs.
+               (copy-file (string-append (assoc-ref (or native-inputs inputs)
+                                                    "nyacc")
                                          "/share/guile/site/3.0/system/ffi-help-rt.scm")
                           "yaml/ffi-help-rt.scm")
                (substitute* "yaml/ffi-help-rt.scm"
                  (("system ffi-help-rt") "yaml ffi-help-rt"))
                #true))
+           ;; TODO when cross-compiling, this fails to find "yaml.h"
            (add-before 'build 'build-ffi
              (lambda* (#:key inputs #:allow-other-keys)
                (invoke "guild" "compile-ffi"
@@ -4584,7 +4907,8 @@ including parsing and code generation.")
       (propagated-inputs
        `(("guile-bytestructures" ,guile-bytestructures)))
       (native-inputs
-       `(("nyacc" ,nyacc)))
+       `(("nyacc" ,nyacc)
+         ("guile" ,guile-3.0)))
       (home-page "https://github.com/mwette/guile-libyaml")
       (synopsis "Guile wrapper for libyaml")
       (description
@@ -4610,9 +4934,9 @@ ffi-helper from nyacc.")
       (build-system cmake-build-system)
       (arguments `(#:tests? #f))
       (native-inputs
-       `(("pkg-config" ,pkg-config)))
-      (inputs
-       `(("guile" ,guile-2.2)))
+       `(("pkg-config" ,pkg-config)
+         ;; only used for tests
+         ("guile" ,guile-2.2)))
       (home-page "https://github.com/arximboldi/schmutz")
       (synopsis "Bind C++ code to Scheme")
       (description "Schmutz is a header-only library to declare Scheme bindings
@@ -4638,7 +4962,9 @@ or @code{LuaBind} but for Scheme.")
      `(("autoconf" ,autoconf)
        ("automake" ,automake)
        ("pkg-config" ,pkg-config)
-       ("texinfo" ,texinfo)))
+       ("texinfo" ,texinfo)
+       ;; for "guild compile" (TODO --target is not set).
+       ("guile" ,guile-3.0)))
     (inputs `(("guile" ,guile-3.0)))
     (synopsis "Guile implementation of CBOR")
     (description
-- 
2.31.0