Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Consider building GHC with Haskell libraries linked in statically #129245

Open
1 task
nh2 opened this issue Jul 4, 2021 · 6 comments
Open
1 task

Consider building GHC with Haskell libraries linked in statically #129245

nh2 opened this issue Jul 4, 2021 · 6 comments

Comments

@nh2
Copy link
Contributor

nh2 commented Jul 4, 2021

GHC in nixpkgs is currently built with DYNAMIC_GHC_PROGRAMS=YES. This links Haskell libraries dynamically into GHC, and makes GHC's startup slow.

That in turn makes GHC a bit of a drag to use with nix, because even a simple --version call is unnecessarily slow (e.g. when used from scripts or in interactive feedback loops).

Here's a table of the startup time we're giving away:

startup time (s) --version time (s)
DYNAMIC_GHC_PROGRAMS=YES 0.30 0.12
DYNAMIC_GHC_PROGRAMS=NO 0.20 0.03
speedup factor 1.5x 4x

Finally, DYNAMIC_GHC_PROGRAMS=YES also makes the nix package larger: 435 MB vs 411 MB for static.

Click here to expand data:

# time /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/bin/ghc          
ghc: no input files
Usage: For basic information, try the `--help' option.
/nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/bin/ghc  0.28s user 0.02s system 98% cpu 0.302 total
# time /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/bin/ghc --version      
The Glorious Glasgow Haskell Compilation System, version 8.10.4
/nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/bin/ghc --version  0.11s user 0.01s system 99% cpu 0.122 total
# ldd /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/ghc
        linux-vdso.so.1 (0x00007fff371f5000)
        libHShaskeline-0.8.0.1-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../haskeline-0.8.0.1/libHShaskeline-0.8.0.1-ghc8.10.4.so (0x00007fe7bc68b000)
        libHSghc-8.10.4-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../ghc-8.10.4/libHSghc-8.10.4-ghc8.10.4.so (0x00007fe7b8e6c000)
        libHSterminfo-0.4.1.4-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../terminfo-0.4.1.4/libHSterminfo-0.4.1.4-ghc8.10.4.so (0x00007fe7b8e3d000)
        libHSprocess-1.6.9.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../process-1.6.9.0/libHSprocess-1.6.9.0-ghc8.10.4.so (0x00007fe7b8e00000)
        libHShpc-0.6.1.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../hpc-0.6.1.0/libHShpc-0.6.1.0-ghc8.10.4.so (0x00007fe7b8dca000)
        libHSghci-8.10.4-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../ghci-8.10.4/libHSghci-8.10.4-ghc8.10.4.so (0x00007fe7b8c3a000)
        libHSghc-heap-8.10.4-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../ghc-heap-8.10.4/libHSghc-heap-8.10.4-ghc8.10.4.so (0x00007fe7b8bd0000)
        libHSghc-boot-8.10.4-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../ghc-boot-8.10.4/libHSghc-boot-8.10.4-ghc8.10.4.so (0x00007fe7b8b2b000)
        libHSbinary-0.8.8.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../binary-0.8.8.0/libHSbinary-0.8.8.0-ghc8.10.4.so (0x00007fe7b8aa1000)
        libHSexceptions-0.10.4-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../exceptions-0.10.4/libHSexceptions-0.10.4-ghc8.10.4.so (0x00007fe7b8a69000)
        libHStemplate-haskell-2.16.0.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../template-haskell-2.16.0.0/libHStemplate-haskell-2.16.0.0-ghc8.10.4.so (0x00007fe7b885e000)
        libHSpretty-1.1.3.6-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../pretty-1.1.3.6/libHSpretty-1.1.3.6-ghc8.10.4.so (0x00007fe7b8800000)
        libHSghc-boot-th-8.10.4-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../ghc-boot-th-8.10.4/libHSghc-boot-th-8.10.4-ghc8.10.4.so (0x00007fe7b87d0000)
        libHSstm-2.5.0.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../stm-2.5.0.0/libHSstm-2.5.0.0-ghc8.10.4.so (0x00007fe7b87a9000)
        libHSmtl-2.2.2-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../mtl-2.2.2/libHSmtl-2.2.2-ghc8.10.4.so (0x00007fe7b8779000)
        libHStransformers-0.5.6.2-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../transformers-0.5.6.2/libHStransformers-0.5.6.2-ghc8.10.4.so (0x00007fe7b86a3000)
        libHSdirectory-1.3.6.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../directory-1.3.6.0/libHSdirectory-1.3.6.0-ghc8.10.4.so (0x00007fe7b8659000)
        libHSunix-2.7.2.2-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../unix-2.7.2.2/libHSunix-2.7.2.2-ghc8.10.4.so (0x00007fe7b8571000)
        libHStime-1.9.3-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../time-1.9.3/libHStime-1.9.3-ghc8.10.4.so (0x00007fe7b8487000)
        libHSfilepath-1.4.2.1-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../filepath-1.4.2.1/libHSfilepath-1.4.2.1-ghc8.10.4.so (0x00007fe7b8457000)
        libHScontainers-0.6.2.1-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../containers-0.6.2.1/libHScontainers-0.6.2.1-ghc8.10.4.so (0x00007fe7b815d000)
        libHSbytestring-0.10.12.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../bytestring-0.10.12.0/libHSbytestring-0.10.12.0-ghc8.10.4.so (0x00007fe7b803a000)
        libHSdeepseq-1.4.4.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../deepseq-1.4.4.0/libHSdeepseq-1.4.4.0-ghc8.10.4.so (0x00007fe7b801f000)
        libHSarray-0.5.4.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../array-0.5.4.0/libHSarray-0.5.4.0-ghc8.10.4.so (0x00007fe7b7f54000)
        libHSbase-4.14.1.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../base-4.14.1.0/libHSbase-4.14.1.0-ghc8.10.4.so (0x00007fe7b7634000)
        libHSinteger-gmp-1.0.3.0-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../integer-gmp-1.0.3.0/libHSinteger-gmp-1.0.3.0-ghc8.10.4.so (0x00007fe7b75f2000)
        libHSghc-prim-0.6.1-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../ghc-prim-0.6.1/libHSghc-prim-0.6.1-ghc8.10.4.so (0x00007fe7b7148000)
        libHSrts_thr-ghc8.10.4.so => /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/lib/ghc-8.10.4/bin/../rts/libHSrts_thr-ghc8.10.4.so (0x00007fe7b70b7000)
        libncursesw.so.6 => /nix/store/s5xpnmnhibl76a47wd65cwrwgjclzrnc-ncurses-6.2/lib/libncursesw.so.6 (0x00007fe7b7046000)
        libgmp.so.10 => /nix/store/157hv8qvfn8wgqjvrbkj69wa72b0if7n-gmp-6.2.1/lib/libgmp.so.10 (0x00007fe7b6fa4000)
        libc.so => /nix/store/dlvw7qab3m24m88f0iwc8zzal06ab92p-musl-1.2.2/lib/libc.so (0x00007fe7b6ef1000)
        libffi.so.7 => /nix/store/c1wiqgajygl66z3n1jl9m9baiykxwp1k-libffi-3.3/lib/libffi.so.7 (0x00007fe7b6ee4000)
# time /nix/store/fh1wc8s9ja3vi9zxgazkp9rp48c4nx7d-ghc-8.10.4/bin/ghc
ghc: no input files
Usage: For basic information, try the `--help' option.
/nix/store/fh1wc8s9ja3vi9zxgazkp9rp48c4nx7d-ghc-8.10.4/bin/ghc  0.18s user 0.01s system 95% cpu 0.204 total
# time /nix/store/fh1wc8s9ja3vi9zxgazkp9rp48c4nx7d-ghc-8.10.4/bin/ghc --version
The Glorious Glasgow Haskell Compilation System, version 8.10.4
/nix/store/fh1wc8s9ja3vi9zxgazkp9rp48c4nx7d-ghc-8.10.4/bin/ghc --version  0.02s user 0.01s system 89% cpu 0.034 total
# ldd /nix/store/fh1wc8s9ja3vi9zxgazkp9rp48c4nx7d-ghc-8.10.4/lib/ghc-8.10.4/bin/ghc
        linux-vdso.so.1 (0x00007fffc5f99000)
        libncursesw.so.6 => /nix/store/s5xpnmnhibl76a47wd65cwrwgjclzrnc-ncurses-6.2/lib/libncursesw.so.6 (0x00007f50f4a13000)
        libgmp.so.10 => /nix/store/157hv8qvfn8wgqjvrbkj69wa72b0if7n-gmp-6.2.1/lib/libgmp.so.10 (0x00007f50f4973000)
        libc.so => /nix/store/dlvw7qab3m24m88f0iwc8zzal06ab92p-musl-1.2.2/lib/libc.so (0x00007f50f48c0000)
        libffi.so.7 => /nix/store/c1wiqgajygl66z3n1jl9m9baiykxwp1k-libffi-3.3/lib/libffi.so.7 (0x00007f50f48b3000)
 # du -sh /nix/store/fh1wc8s9ja3vi9zxgazkp9rp48c4nx7d-ghc-8.10.4/lib/ghc-8.10.4
411M    /nix/store/fh1wc8s9ja3vi9zxgazkp9rp48c4nx7d-ghc-8.10.4/lib/ghc-8.10.4

# du -sh /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/
435M    /nix/store/ipdnx5ajcdplxvsff6lw55pdwsm8qpn6-ghc-8.10.4/

In nixpkgs there is no benefit in linking Haskell libraries dynamically into programs. This is why the haskell-modules/generic-builder.nix defaults to enableSharedExecutables ? false for nix-built Haskell programs. We should do the same for GHC.

CC @NixOS/haskell @domenkozar


Edit: We should not do that for now, see #129245 (comment).

Instead, new closing criteria for this issue:

  • Find an authorative resource or technical explanation of why exactly this would create problems, and put that in a comment on enableShared it in the GHC Nix derivation files.
@maralorn
Copy link
Member

maralorn commented Jul 4, 2021

Sounds good to me, thank you for figuring this out!

@nh2
Copy link
Contributor Author

nh2 commented Jul 5, 2021

I asked on #ghc chat and got suggestions that this is probably not a good idea:

@mpickering says:

There are a lot of issues with the linker built into GHC, so TH will not work with nixpkgs provided GHC for some cases.
If you need to dynamically load certain libraries, just look at the HLS issue tracker.

@adamse concurs:

I agree with mpickering that it will cause pain for TH and sometimes ghci.


My original question was:

I'm planning to switch the nixpkgs GHC buidls from defaulting to DYNAMIC_GHC_PROGRAMS=YES to NO, to get 4x faster-starting GHCs. Will this prevent the creation of .so files entirely, thus making dynamic linking impossible, or will -dynamic-too still be active?

the latter part of which @adamse explained:

You can still build .so's (with or w/o -dynamic-too), but [concerns quoted above]


@mpickering explained that haskell-language-server distributes GHCs with Haskell libraries statically-linked in, and that this creates many problems for them. It is currently unclear to me why haskell-language-server does that then, as it seems that they could just as well provide a DYNAMIC_GHC_PROGRAMS=YES for download for e.g. VSCode users. I asked that upstream: haskell/haskell-language-server#2000


I don't really understand why linking e.g. libHSfilepath-* statically into the ghc binary affects TemplateHaskell at all. If anybody could find a resource that we could link to from the GHC nix derivations, we could close this ticket as something we don't want to do.

@nh2 nh2 changed the title Build GHC with Haskell libraries linked in statically Consider building GHC with Haskell libraries linked in statically Jul 5, 2021
@nh2
Copy link
Contributor Author

nh2 commented Jul 5, 2021

I don't really understand why linking e.g. libHSfilepath-* statically into the ghc binary affects TemplateHaskell at all. If anybody could find a resource that we could link to from the GHC nix derivations, we could close this ticket as something we don't want to do.

@mpickering / @adamse / @bgamari If you have time, could you help us out with a good explanation or upstream GHC ticket to link to?

@adamse
Copy link
Contributor

adamse commented Jul 21, 2021

I think the main issue is linking the RTS statically, this currently causes GHCi and TemplateHaskell to use the home grown runtime linker to load other haskell packages object code. I don't quite remember all the details here though.

I think that on some targets it would be possible to use dlopen instead of the ghc rts linker even with a statically linked rts (with ld's --dynamic-list for rts symbols), but this requires work on GHC and I understand that not all targets have a functioning dl library (musl?).

@stale
Copy link

stale bot commented May 1, 2022

I marked this as stale due to inactivity. → More info

@stale stale bot added the 2.status: stale https://github.com/NixOS/nixpkgs/blob/master/.github/STALE-BOT.md label May 1, 2022
@NorfairKing
Copy link
Contributor

Definitely not stale.

@stale stale bot removed the 2.status: stale https://github.com/NixOS/nixpkgs/blob/master/.github/STALE-BOT.md label Jun 3, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants