On Thu, Feb 15, 2024 at 11:29:55AM +0100, Konrad Hinsen wrote:
> Hi Saku,
> 
> > Maybe someone else can give more general or Guix specific advice on
> > finding out the cause of such problems, but I believe that in this case
> > the fix would just be packaging GHC for aarch64-linux. It should[1] be
> > possible but it will require some work.
> >
> > [1]: https://gitlab.haskell.org/ghc/ghc/-/wikis/platforms
> 
> Thanks for the pointer! It looks indeed like GHC already support
> aarch64, so it's just a matter of integrating that support into Guix.
> I'll see if I can find someone motivated and competent to do that.

I've been carrying around this diff for a while but I don't think I'm
currently ready to finish it off. It adds aarch64 and armhf bootstrap
binaries for GHC and gets started on the path to building ghc-8.6 with
them.

-- 
Efraim Flashner   <efr...@flashner.co.il>   רנשלפ םירפא
GPG key = A28B F40C 3E55 1372 662D  14F7 41AA E7DC CA3D 8351
Confidentiality cannot be guaranteed on emails sent or received unencrypted
diff --git a/gnu/packages/haskell.scm b/gnu/packages/haskell.scm
index 62815efbb1..92ba976189 100644
--- a/gnu/packages/haskell.scm
+++ b/gnu/packages/haskell.scm
@@ -57,6 +57,7 @@ (define-module (gnu packages haskell)
   #:use-module (gnu packages libffi)
   #:use-module (gnu packages linux)
   #:use-module (gnu packages lisp)
+  #:use-module (gnu packages llvm)
   #:use-module (gnu packages m4)
   #:use-module (gnu packages multiprecision)
   #:use-module (gnu packages ncurses)
@@ -699,6 +852,24 @@ (define ghc-bootstrap-i686-7.8.4
      (base32
       "0wj5s435j0zgww70bj1d3f6wvnnpzlxwvwcyh2qv4qjq5z8j64kg"))))
 
+(define ghc-bootstrap-armhf-8.2.2
+  (origin
+    (method url-fetch)
+    (uri
+     
"https://downloads.haskell.org/~ghc/8.2.2/ghc-8.2.2-armv7-deb8-linux.tar.xz";)
+    (sha256
+     (base32
+      "1jmv8qmnh5bn324fivbwdcaj55kvw7cb2zq9pafmlmv3qwwx7s46"))))
+
+(define ghc-bootstrap-aarch64-8.2.2
+  (origin
+    (method url-fetch)
+    (uri
+     
"https://downloads.haskell.org/~ghc/8.2.2/ghc-8.2.2-aarch64-deb8-linux.tar.xz";)
+    (sha256
+     (base32
+      "1k2amylcp1ad67c75h1pqf7czf9m0zj1i7hdc45ghjklnfq9hrk7"))))
+
 ;; 43 tests out of 3965 fail.
 ;;
 ;; Most of them do not appear to be serious:
@@ -1057,10 +1228,115 @@ (define-public ghc-8.4
                                 (file-pattern ".*\\.conf\\.d$")
                                 (file-type 'directory))))))
 
+(define ghc-8.4-bootstrap
+  (package
+    (inherit ghc-8.4)
+    (name "ghc")
+    (version "8.4.4")
+    (supported-systems '("aarch64-linux" "armhf-linux"))
+    (native-inputs
+     `(;("clang" ,clang)
+       ("gcc:lib" ,gcc "lib")
+       ("ghc-bootstrap" ,(if (target-aarch64?)
+                           ghc-bootstrap-aarch64-8.2.2
+                           ghc-bootstrap-armhf-8.2.2))
+       ("llvm" ,llvm-9)
+       ("patchelf" ,patchelf)
+       ;("ld-wrapper" ,(@ (gnu packages commencement) ld-gold-wrapper)) ; for 
arm
+       ,@(filter (match-lambda
+                   (("ghc-bootstrap" . _) #f)
+                   (_ #t))
+                 (package-native-inputs ghc-8.4))))
+    (arguments
+     (substitute-keyword-arguments (package-arguments ghc-8.4)
+       ((#:modules _ #~%gnu-build-system-modules)
+        '((guix build gnu-build-system)
+          (guix build utils)
+          (srfi srfi-26)
+          (srfi srfi-1)))
+       ((#:phases phases)
+        #~(let* ((ghc-bootstrap-path
+                   (string-append (getcwd) "/" #$name "-" #$version 
"/ghc-bin"))
+                 (ghc-bootstrap-prefix
+                   (string-append ghc-bootstrap-path "/usr")))
+            (modify-phases #$phases
+              (add-after 'unpack 'unpack-bin
+                (lambda* (#:key inputs #:allow-other-keys)
+                  (mkdir-p ghc-bootstrap-prefix)
+                  (with-directory-excursion ghc-bootstrap-path
+                    (invoke "tar" "xvf" (assoc-ref inputs "ghc-bootstrap")))))
+              (add-before 'configure 'install-bin
+                (lambda _
+                  (with-directory-excursion
+                    (string-append ghc-bootstrap-path "/ghc-8.2.2")
+                    (invoke "make" "install"))))
+              (add-before 'install-bin 'configure-bin
+                (lambda* (#:key inputs outputs #:allow-other-keys)
+                  (let* ((binaries
+                           (list "ghc/stage2/build/tmp/ghc-stage2"
+                                 "iserv/stage2/build/tmp/ghc-iserv"
+                                 "iserv/stage2_dyn/build/tmp/ghc-iserv-dyn"
+                                 "iserv/stage2_p/build/tmp/ghc-iserv-prof"
+                                 
"utils/ghc-cabal/dist-install/build/tmp/ghc-cabal"
+                                 "utils/ghc-pkg/dist-install/build/tmp/ghc-pkg"
+                                 ;"utils/haddock/dist/build/tmp/haddock" ; not 
on arm
+                                 "utils/hp2ps/dist/build/tmp/hp2ps"
+                                 "utils/hpc/dist-install/build/tmp/hpc"
+                                 "utils/hsc2hs/dist-install/build/tmp/hsc2hs"
+                                 "utils/runghc/dist-install/build/tmp/runghc"
+                                 "utils/unlit/dist/build/tmp/unlit"))
+                         (gmp (assoc-ref inputs "gmp"))
+                         (gmp-lib (string-append gmp "/lib"))
+                         (gmp-include (string-append gmp "/include"))
+                         (ncurses-lib
+                           (dirname (search-input-file inputs 
"/lib/libncurses.so")))
+                         (ld-so (search-input-file inputs 
#$(glibc-dynamic-linker)))
+                         (libtinfo-dir
+                           (string-append ghc-bootstrap-prefix
+                                          "/lib/ghc-8.2.2/terminfo-0.4.1.0")))
+                    (with-directory-excursion
+                      (string-append ghc-bootstrap-path "/ghc-8.2.2")
+                      (setenv "CONFIG_SHELL" (which "bash"))
+                      (setenv "LD_LIBRARY_PATH"
+                              (string-append gmp-lib ":"
+                                             (assoc-ref inputs "gcc:lib") 
"/lib"))
+                      ;; The binaries have "/lib64/ld-linux-x86-64.so.2" 
hardcoded.
+                      (for-each
+                        (cut invoke "patchelf" "--set-interpreter" ld-so <>)
+                        binaries)
+                      ;; The binaries include a reference to libtinfo.so.5 
which
+                      ;; is a subset of libncurses.so.5.  We create a symlink 
in a
+                      ;; directory included in the bootstrap binaries rpath.
+                      (mkdir-p libtinfo-dir)
+                      (symlink
+                        (string-append ncurses-lib "/libncursesw.so."
+                                       ;; Extract "6.2" from "6.2.20210619" if 
a
+                                       ;; dash-separated version tag exists.
+                                       #$(let* ((v (package-version ncurses))
+                                                (d (or (string-index v #\-)
+                                                       (string-length v))))
+                                           (version-major+minor (string-take v 
d))))
+                        (string-append libtinfo-dir "/libtinfo.so.5"))
+
+                      (setenv "PATH"
+                              (string-append (getenv "PATH") ":"
+                                             ghc-bootstrap-prefix "/bin"))
+                      (invoke
+                        (string-append (getcwd) "/configure")
+                        (string-append "--prefix=" 
ghc-bootstrap-prefix)))))))))))
+    (native-search-paths (list (search-path-specification
+                                (variable "GHC_PACKAGE_PATH")
+                                (files (list
+                                        (string-append "lib/ghc-" version)))
+                                (file-pattern ".*\\.conf\\.d$")
+                                (file-type 'directory))))))
+
 (define-public ghc-8.6
   (package (inherit ghc-8.4)
     (name "ghc")
     (version "8.6.5")
+    (supported-systems (append (package-supported-systems ghc-8.4)
+                               (package-supported-systems ghc-8.4-bootstrap)))
     (source
      (origin
        (method url-fetch)
@@ -1070,7 +1346,10 @@ (define-public ghc-8.6
         (base32 "0qg3zsmbk4rkwkc3jpas3zs74qaxmw4sp4v1mhsbj0a0dzls2jjd"))))
     (native-inputs
      `(;; GHC 8.6.5 must be built with GHC >= 8.2.
-       ("ghc-bootstrap" ,ghc-8.4)
+       ("ghc-bootstrap" ,(if (member (%current-system)
+                                     (package-supported-systems 
ghc-8.4-bootstrap))
+                           ghc-8.4-bootstrap
+                           ghc-8.4))
        ("ghc-testsuite"
         ,(origin
            (method url-fetch)
@@ -1140,6 +1419,105 @@ (define-public ghc-8.6
                                 (file-pattern ".*\\.conf\\.d$")
                                 (file-type 'directory))))))
 
+(define ghc-8.6-bootstrap
+  (package
+    (inherit ghc-8.6)
+    (name "ghc")
+    (version "8.6.5")
+    (supported-systems '("aarch64-linux" "armhf-linux"))
+    (native-inputs
+     `(;("clang" ,clang)
+       ("gcc:lib" ,gcc "lib")
+       ("ghc-bootstrap" ,(if (target-aarch64?)
+                           ghc-bootstrap-aarch64-8.2.2
+                           ghc-bootstrap-armhf-8.2.2))
+       ("llvm" ,llvm)
+       ("patchelf" ,patchelf)
+       ,@(filter (match-lambda
+                   (("ghc-bootstrap" . _) #f)
+                   (_ #t))
+                 (package-native-inputs ghc-8.6))))
+    (arguments
+     (substitute-keyword-arguments (package-arguments ghc-8.6)
+       ((#:modules _ #~%gnu-build-system-modules)
+        '((guix build gnu-build-system)
+          (guix build utils)
+          (srfi srfi-26)
+          (srfi srfi-1)))
+       ((#:phases phases)
+        #~(let* ((ghc-bootstrap-path
+                   (string-append (getcwd) "/" #$name "-" #$version 
"/ghc-bin"))
+                 (ghc-bootstrap-prefix
+                   (string-append ghc-bootstrap-path "/usr")))
+            (modify-phases #$phases
+              (add-after 'unpack 'unpack-bin
+                (lambda* (#:key inputs #:allow-other-keys)
+                  (mkdir-p ghc-bootstrap-prefix)
+                  (with-directory-excursion ghc-bootstrap-path
+                    (invoke "tar" "xvf" (assoc-ref inputs "ghc-bootstrap")))))
+              (add-before 'configure 'install-bin
+                (lambda _
+                  (with-directory-excursion
+                    (string-append ghc-bootstrap-path "/ghc-8.2.2")
+                    (invoke "make" "install"))))
+              (add-before 'install-bin 'configure-bin
+                (lambda* (#:key inputs outputs #:allow-other-keys)
+                  (let* ((binaries
+                           (list "ghc/stage2/build/tmp/ghc-stage2"
+                                 
"utils/ghc-cabal/dist-install/build/tmp/ghc-cabal"
+                                 "utils/ghc-pkg/dist-install/build/tmp/ghc-pkg"
+                                 "utils/haddock/dist/build/tmp/haddock"
+                                 "utils/hp2ps/dist/build/tmp/hp2ps"
+                                 "utils/hpc/dist-install/build/tmp/hpc"
+                                 "utils/hsc2hs/dist-install/build/tmp/hsc2hs"
+                                 "utils/runghc/dist-install/build/tmp/runghc"
+                                 "utils/unlit/dist/build/tmp/unlit"))
+                         (gmp (assoc-ref inputs "gmp"))
+                         (gmp-lib (string-append gmp "/lib"))
+                         (gmp-include (string-append gmp "/include"))
+                         (ncurses-lib
+                           (dirname (search-input-file inputs 
"/lib/libncurses.so")))
+                         (ld-so (search-input-file inputs 
#$(glibc-dynamic-linker)))
+                         (libtinfo-dir
+                           (string-append ghc-bootstrap-prefix
+                                          "/lib/ghc-8.2.2/terminfo-0.4.1.0")))
+                    (with-directory-excursion
+                      (string-append ghc-bootstrap-path "/ghc-8.2.2")
+                      (setenv "CONFIG_SHELL" (which "bash"))
+                      (setenv "LD_LIBRARY_PATH"
+                              (string-append gmp-lib ":"
+                                             (assoc-ref inputs "gcc:lib") 
"/lib"))
+                      ;; The binaries have "/lib64/ld-linux-x86-64.so.2" 
hardcoded.
+                      (for-each
+                        (cut invoke "patchelf" "--set-interpreter" ld-so <>)
+                        binaries)
+                      ;; The binaries include a reference to libtinfo.so.5 
which
+                      ;; is a subset of libncurses.so.5.  We create a symlink 
in a
+                      ;; directory included in the bootstrap binaries rpath.
+                      (mkdir-p libtinfo-dir)
+                      (symlink
+                        (string-append ncurses-lib "/libncursesw.so."
+                                       ;; Extract "6.2" from "6.2.20210619" if 
a
+                                       ;; dash-separated version tag exists.
+                                       #$(let* ((v (package-version ncurses))
+                                                (d (or (string-index v #\-)
+                                                       (string-length v))))
+                                           (version-major+minor (string-take v 
d))))
+                        (string-append libtinfo-dir "/libtinfo.so.5"))
+
+                      (setenv "PATH"
+                              (string-append (getenv "PATH") ":"
+                                             ghc-bootstrap-prefix "/bin"))
+                      (invoke
+                        (string-append (getcwd) "/configure")
+                        (string-append "--prefix=" 
ghc-bootstrap-prefix)))))))))))
+    (native-search-paths (list (search-path-specification
+                                (variable "GHC_PACKAGE_PATH")
+                                (files (list
+                                        (string-append "lib/ghc-" version)))
+                                (file-pattern ".*\\.conf\\.d$")
+                                (file-type 'directory))))))
+
 (define-public ghc-8.8
   (package (inherit ghc-8.6)
     (name "ghc")

Attachment: signature.asc
Description: PGP signature

Reply via email to