@@ -1,235 +0,0 @@
{ stdenv , targetPackages
# build-tools
, bootPkgs
, autoconf , automake , coreutils , fetchurl , fetchpatch , perl , python3 , m4 , sphinx
, libiconv ? null , ncurses
, # GHC can be built with system libffi or a bundled one.
libffi ? null
, useLLVM ? ! stdenv . targetPlatform . isx86 || ( stdenv . targetPlatform . isMusl && stdenv . hostPlatform != stdenv . targetPlatform )
, # LLVM is conceptually a run-time-only depedendency, but for
# non-x86, we need LLVM to bootstrap later stages, so it becomes a
# build-time dependency too.
buildLlvmPackages , llvmPackages
, # If enabled, GHC will be built with the GPL-free but slower integer-simple
# library instead of the faster but GPLed integer-gmp library.
enableIntegerSimple ? ! ( stdenv . lib . any ( stdenv . lib . meta . platformMatch stdenv . hostPlatform ) gmp . meta . platforms ) , gmp
, # If enabled, use -fPIC when compiling static libs.
enableRelocatedStaticLibs ? stdenv . targetPlatform != stdenv . hostPlatform
, # Whether to build dynamic libs for the standard library (on the target
# platform). Static libs are always built.
enableShared ? ! stdenv . targetPlatform . isWindows && ! stdenv . targetPlatform . useiOSPrebuilt
, # Whetherto build terminfo.
enableTerminfo ? ! stdenv . targetPlatform . isWindows
, # What flavour to build. An empty string indicates no
# specific flavour and falls back to ghc default values.
ghcFlavour ? stdenv . lib . optionalString ( stdenv . targetPlatform != stdenv . hostPlatform ) " p e r f - c r o s s "
}:
assert ! enableIntegerSimple -> gmp != null ;
let
inherit ( stdenv ) buildPlatform hostPlatform targetPlatform ;
inherit ( bootPkgs ) ghc ;
# TODO(@Ericson2314) Make unconditional
targetPrefix = stdenv . lib . optionalString
( targetPlatform != hostPlatform )
" ${ targetPlatform . config } - " ;
buildMK = ''
B u i l d F l a v o u r = ${ ghcFlavour }
i f n e q \ " \ $( B u i l d F l a v o u r ) \ " \ " \ "
i n c l u d e m k / f l a v o u r s / \ $( B u i l d F l a v o u r ) . m k
e n d i f
D Y N A M I C _ G H C _ P R O G R A M S = ${ if enableShared then " Y E S " else " N O " }
I N T E G E R _ L I B R A R Y = ${ if enableIntegerSimple then " i n t e g e r - s i m p l e " else " i n t e g e r - g m p " }
'' + stdenv . lib . optionalString ( targetPlatform != hostPlatform ) ''
S t a g e 1 O n l y = ${ if targetPlatform . system = = hostPlatform . system then " N O " else " Y E S " }
C r o s s C o m p i l e P r e f i x = ${ targetPrefix }
H A D D O C K _ D O C S = N O
B U I L D _ S P H I N X _ H T M L = N O
B U I L D _ S P H I N X _ P D F = N O
'' + stdenv . lib . optionalString enableRelocatedStaticLibs ''
G h c L i b H c O p t s + = - f P I C
G h c R t s H c O p t s + = - f P I C
'' + stdenv . lib . optionalString targetPlatform . useAndroidPrebuilt ''
E X T R A _ C C _ O P T S + = - s t d = g n u 9 9
'' ;
# Splicer will pull out correct variations
libDeps = platform : stdenv . lib . optional enableTerminfo [ ncurses ]
++ [ libffi ]
++ stdenv . lib . optional ( ! enableIntegerSimple ) gmp
++ stdenv . lib . optional ( platform . libc != " g l i b c " && ! targetPlatform . isWindows ) libiconv ;
toolsForTarget =
if hostPlatform = = buildPlatform then
[ targetPackages . stdenv . cc ] ++ stdenv . lib . optional useLLVM llvmPackages . llvm
else assert targetPlatform = = hostPlatform ; # build != host == target
[ stdenv . cc ] ++ stdenv . lib . optional useLLVM buildLlvmPackages . llvm ;
targetCC = builtins . head toolsForTarget ;
in
stdenv . mkDerivation ( rec {
version = " 8 . 6 . 3 " ;
name = " ${ targetPrefix } g h c - ${ version } " ;
src = fetchurl {
url = " h t t p s : / / d o w n l o a d s . h a s k e l l . o r g / ~ g h c / ${ version } / g h c - ${ version } - s r c . t a r . x z " ;
sha256 = " 0 8 v z q 0 d p g 4 a 3 9 b s 6 1 j 6 r q 4 z 0 n 7 j b y 5 m c 6 9 h 4 m 2 5 x h d 8 r j y v k g 7 l z " ;
} ;
enableParallelBuilding = true ;
outputs = [ " o u t " " d o c " ] ;
patches = [ ( fetchpatch rec { # https://phabricator.haskell.org/D5123
url = " h t t p : / / t a r b a l l s . n i x o s . o r g / s h a 2 5 6 / ${ sha256 } " ;
name = " D 5 1 2 3 . d i f f " ;
sha256 = " 0 n h q w d a m f 2 y 4 g b w q x c g j x s 0 k q x 2 3 w 9 g v 5 k j 0 z v 6 4 5 0 d q 1 9 r j i 8 2 n " ;
} ) ] ;
postPatch = " p a t c h S h e b a n g s . " ;
# GHC is a bit confused on its cross terminology.
preConfigure = ''
f o r e n v i n $( e n v | g r e p ' ^ T A R G E T _ ' | s e d - E ' s | \ + ? = . * | | ' ) ; d o
e x p o r t " ''$ { e n v # T A R G E T _ } = ''$ { ! e n v } "
d o n e
# G H C i s a b i t c o n f u s e d o n i t s c r o s s t e r m i n o l o g y , a s t h e s e w o u l d n o r m a l l y b e
# t h e * h o s t * t o o l s .
e x p o r t C C = " ${ targetCC } / b i n / ${ targetCC . targetPrefix } c c "
e x p o r t C X X = " ${ targetCC } / b i n / ${ targetCC . targetPrefix } c x x "
# U s e g o l d t o w o r k a r o u n d h t t p s : / / s o u r c e w a r e . o r g / b u g z i l l a / s h o w _ b u g . c g i ? i d = 1 6 1 7 7
e x p o r t L D = " ${ targetCC . bintools } / b i n / ${ targetCC . bintools . targetPrefix } l d ${ stdenv . lib . optionalString targetPlatform . isAarch32 " . g o l d " } "
e x p o r t A S = " ${ targetCC . bintools . bintools } / b i n / ${ targetCC . bintools . targetPrefix } a s "
e x p o r t A R = " ${ targetCC . bintools . bintools } / b i n / ${ targetCC . bintools . targetPrefix } a r "
e x p o r t N M = " ${ targetCC . bintools . bintools } / b i n / ${ targetCC . bintools . targetPrefix } n m "
e x p o r t R A N L I B = " ${ targetCC . bintools . bintools } / b i n / ${ targetCC . bintools . targetPrefix } r a n l i b "
e x p o r t R E A D E L F = " ${ targetCC . bintools . bintools } / b i n / ${ targetCC . bintools . targetPrefix } r e a d e l f "
e x p o r t S T R I P = " ${ targetCC . bintools . bintools } / b i n / ${ targetCC . bintools . targetPrefix } s t r i p "
e c h o - n " ${ buildMK } " > m k / b u i l d . m k
s e d - i - e ' s | - i s y s r o o t / D e v e l o p e r / S D K s / M a c O S X 1 0 . 5 . s d k | | ' c o n f i g u r e
'' + stdenv . lib . optionalString ( ! stdenv . isDarwin ) ''
e x p o r t N I X _ L D F L A G S + = " - r p a t h $o u t / l i b / g h c - ${ version } "
'' + stdenv . lib . optionalString stdenv . isDarwin ''
e x p o r t N I X _ L D F L A G S + = " - n o _ d t r a c e _ d o f "
'' + stdenv . lib . optionalString targetPlatform . useAndroidPrebuilt ''
s e d - i - e ' 5 i , ( " a r m v 7 a - u n k n o w n - l i n u x - a n d r o i d e a b i " , ( " e - m : e - p : 3 2 : 3 2 - i 6 4 : 6 4 - v 1 2 8 : 6 4 : 1 2 8 - a : 0 : 3 2 - n 3 2 - S 6 4 " , " c o r t e x - a 8 " , " " ) ) ' l l v m - t a r g e t s
'' + stdenv . lib . optionalString targetPlatform . isMusl ''
e c h o " p a t c h i n g l l v m - t a r g e t s f o r m u s l t a r g e t s . . . "
e c h o " C l o n i n g t h e s e e x i s t i n g ' * - l i n u x - g n u * ' t a r g e t s : "
g r e p l i n u x - g n u l l v m - t a r g e t s | s e d ' s / ^ / / '
e c h o " ( g o g o g a d g e t s e d ) "
s e d - i ' s , \ ( ^ . * l i n u x - \ ) g n u \ ( . * \ ) $, \ 0 \ n \ 1 m u s l \ 2 , ' l l v m - t a r g e t s
e c h o " l l v m - t a r g e t s n o w c o n t a i n s t h e s e ' * - l i n u x - m u s l * ' t a r g e t s : "
g r e p l i n u x - m u s l l l v m - t a r g e t s | s e d ' s / ^ / / '
e c h o " A n d n o w p a t c h i n g t o p r e s e r v e ' - m u s l e a b i ' a s d o n e w i t h ' - g n u e a b i ' "
# ( a c l o c a l . m 4 i s a c t u a l s o u r c e , b u t p a t c h c o n f i g u r e a s w e l l s i n c e w e d o n ' t r e - g e n )
f o r x i n c o n f i g u r e a c l o c a l . m 4 ; d o
s u b s t i t u t e I n P l a c e $x \
- - r e p l a c e ' * - a n d r o i d * | * - g n u e a b i * ) ' \
' * - a n d r o i d * | * - g n u e a b i * | * - m u s l e a b i * ) '
d o n e
'' ;
# TODO(@Ericson2314): Always pass "--target" and always prefix.
configurePlatforms = [ " b u i l d " " h o s t " ]
++ stdenv . lib . optional ( targetPlatform != hostPlatform ) " t a r g e t " ;
# `--with` flags for libraries needed for RTS linker
configureFlags = [
" - - d a t a d i r = $ d o c / s h a r e / d o c / g h c "
" - - w i t h - c u r s e s - i n c l u d e s = ${ ncurses . dev } / i n c l u d e " " - - w i t h - c u r s e s - l i b r a r i e s = ${ ncurses . out } / l i b "
] ++ stdenv . lib . optionals ( libffi != null ) [ " - - w i t h - s y s t e m - l i b f f i " " - - w i t h - f f i - i n c l u d e s = ${ libffi . dev } / i n c l u d e " " - - w i t h - f f i - l i b r a r i e s = ${ libffi . out } / l i b "
] ++ stdenv . lib . optional ( targetPlatform = = hostPlatform && ! enableIntegerSimple ) [
" - - w i t h - g m p - i n c l u d e s = ${ targetPackages . gmp . dev } / i n c l u d e " " - - w i t h - g m p - l i b r a r i e s = ${ targetPackages . gmp . out } / l i b "
] ++ stdenv . lib . optional ( targetPlatform = = hostPlatform && hostPlatform . libc != " g l i b c " && ! targetPlatform . isWindows ) [
" - - w i t h - i c o n v - i n c l u d e s = ${ libiconv } / i n c l u d e " " - - w i t h - i c o n v - l i b r a r i e s = ${ libiconv } / l i b "
] ++ stdenv . lib . optionals ( targetPlatform != hostPlatform ) [
" - - e n a b l e - b o o t s t r a p - w i t h - d e v e l - s n a p s h o t "
] ++ stdenv . lib . optionals ( targetPlatform . isAarch32 ) [
" C F L A G S = - f u s e - l d = g o l d "
" C O N F _ G C C _ L I N K E R _ O P T S _ S T A G E 1 = - f u s e - l d = g o l d "
" C O N F _ G C C _ L I N K E R _ O P T S _ S T A G E 2 = - f u s e - l d = g o l d "
] ++ stdenv . lib . optionals ( targetPlatform . isDarwin && targetPlatform . isAarch64 ) [
# fix for iOS: https://www.reddit.com/r/haskell/comments/4ttdz1/building_an_osxi386_to_iosarm64_cross_compiler/d5qvd67/
" - - d i s a b l e - l a r g e - a d d r e s s - s p a c e "
] ;
# Make sure we never relax`$PATH` and hooks support for compatability.
strictDeps = true ;
# Don’ t add -liconv to LDFLAGS automatically so that GHC will add it itself.
dontAddExtraLibs = true ;
nativeBuildInputs = [
perl autoconf automake m4 python3 sphinx
ghc bootPkgs . alex bootPkgs . happy bootPkgs . hscolour
] ;
# For building runtime libs
depsBuildTarget = toolsForTarget ;
buildInputs = [ perl ] ++ ( libDeps hostPlatform ) ;
propagatedBuildInputs = [ targetPackages . stdenv . cc ]
++ stdenv . lib . optional useLLVM llvmPackages . llvm ;
depsTargetTarget = map stdenv . lib . getDev ( libDeps targetPlatform ) ;
depsTargetTargetPropagated = map ( stdenv . lib . getOutput " o u t " ) ( libDeps targetPlatform ) ;
# required, because otherwise all symbols from HSffi.o are stripped, and
# that in turn causes GHCi to abort
stripDebugFlags = [ " - S " ] ++ stdenv . lib . optional ( ! targetPlatform . isDarwin ) " - - k e e p - f i l e - s y m b o l s " ;
checkTarget = " t e s t " ;
hardeningDisable = [ " f o r m a t " ] ++ stdenv . lib . optional stdenv . targetPlatform . isMusl " p i e " ;
postInstall = ''
# I n s t a l l t h e b a s h c o m p l e t i o n f i l e .
i n s t a l l - D - m 4 4 4 u t i l s / c o m p l e t i o n / g h c . b a s h $o u t / s h a r e / b a s h - c o m p l e t i o n / c o m p l e t i o n s / ${ targetPrefix } g h c
# P a t c h s c r i p t s t o i n c l u d e " r e a d e l f " a n d " c a t " i n $P A T H .
f o r i i n " $o u t / b i n / " * ; d o
t e s t ! - h $i | | c o n t i n u e
e g r e p - - q u i e t ' ^ # ! ' < ( h e a d - n 1 $i ) | | c o n t i n u e
s e d - i - e ' 2 i e x p o r t P A T H = " $P A T H : ${ stdenv . lib . makeBinPath [ targetPackages . stdenv . cc . bintools coreutils ] } " ' $i
d o n e
'' ;
passthru = {
inherit bootPkgs targetPrefix ;
inherit llvmPackages ;
inherit enableShared ;
# Our Cabal compiler name
haskellCompilerName = " g h c - 8 . 6 . 3 " ;
} ;
meta = {
homepage = http://haskell.org/ghc ;
description = " T h e G l a s g o w H a s k e l l C o m p i l e r " ;
maintainers = with stdenv . lib . maintainers ; [ marcweber andres peti ] ;
inherit ( ghc . meta ) license platforms ;
} ;
} // stdenv . lib . optionalAttrs targetPlatform . useAndroidPrebuilt {
dontStrip = true ;
dontPatchELF = true ;
noAuditTmpdir = true ;
} )