at master 9.3 kB view raw
1{ 2 minor_version, 3 major_version, 4 patch_version, 5 patches ? [ ], 6 ... 7}@args: 8let 9 versionNoPatch = "${toString major_version}.${toString minor_version}"; 10 version = "${versionNoPatch}.${toString patch_version}"; 11 safeX11 = 12 stdenv: 13 !(stdenv.hostPlatform.isAarch32 || stdenv.hostPlatform.isMips || stdenv.hostPlatform.isStatic); 14in 15 16{ 17 lib, 18 stdenv, 19 fetchurl, 20 ncurses, 21 binutils, 22 buildEnv, 23 libunwind, 24 fetchpatch, 25 libX11, 26 xorgproto, 27 useX11 ? safeX11 stdenv && lib.versionOlder version "4.09", 28 aflSupport ? false, 29 flambdaSupport ? false, 30 spaceTimeSupport ? false, 31 unsafeStringSupport ? false, 32 framePointerSupport ? false, 33 noNakedPointers ? false, 34}: 35 36assert useX11 -> safeX11 stdenv; 37assert aflSupport -> lib.versionAtLeast version "4.05"; 38assert flambdaSupport -> lib.versionAtLeast version "4.03"; 39assert spaceTimeSupport -> lib.versionAtLeast version "4.04" && lib.versionOlder version "4.12"; 40assert unsafeStringSupport -> lib.versionAtLeast version "4.06" && lib.versionOlder version "5.0"; 41assert framePointerSupport -> lib.versionAtLeast version "4.01"; 42assert noNakedPointers -> lib.versionAtLeast version "4.02" && lib.versionOlder version "5.0"; 43 44let 45 src = 46 args.src or (fetchurl { 47 url = 48 args.url or "http://caml.inria.fr/pub/distrib/ocaml-${versionNoPatch}/ocaml-${version}.tar.xz"; 49 inherit (args) sha256; 50 }); 51in 52 53let 54 useNativeCompilers = !stdenv.hostPlatform.isMips && !stdenv.hostPlatform.isLoongArch64; 55 inherit (lib) 56 optional 57 optionals 58 optionalString 59 strings 60 concatStrings 61 ; 62 pname = concatStrings [ 63 "ocaml" 64 (optionalString aflSupport "+afl") 65 (optionalString spaceTimeSupport "+spacetime") 66 (optionalString flambdaSupport "+flambda") 67 (optionalString framePointerSupport "+fp") 68 ]; 69in 70 71let 72 x11env = buildEnv { 73 name = "x11env"; 74 paths = [ 75 libX11 76 xorgproto 77 ]; 78 }; 79 x11lib = x11env + "/lib"; 80 x11inc = x11env + "/include"; 81 82 fetchpatch' = x: if builtins.isAttrs x then fetchpatch x else x; 83in 84 85stdenv.mkDerivation ( 86 args 87 // { 88 89 inherit pname version src; 90 91 patches = map fetchpatch' patches; 92 93 strictDeps = true; 94 95 prefixKey = "-prefix "; 96 configureFlags = 97 let 98 flags = new: old: if lib.versionAtLeast version "4.08" then new else old; 99 in 100 optionals useX11 ( 101 flags 102 [ "--x-libraries=${x11lib}" "--x-includes=${x11inc}" ] 103 [ "-x11lib" x11lib "-x11include" x11inc ] 104 ) 105 ++ optional aflSupport (flags "--with-afl" "-afl-instrument") 106 ++ optional flambdaSupport (flags "--enable-flambda" "-flambda") 107 ++ optional spaceTimeSupport (flags "--enable-spacetime" "-spacetime") 108 ++ optional framePointerSupport (flags "--enable-frame-pointers" "-with-frame-pointers") 109 ++ optionals unsafeStringSupport [ 110 "--disable-force-safe-string" 111 "DEFAULT_STRING=unsafe" 112 ] 113 ++ optional (stdenv.hostPlatform.isStatic && (lib.versionOlder version "4.08")) "-no-shared-libs" 114 ++ optionals (stdenv.hostPlatform != stdenv.buildPlatform && lib.versionOlder version "4.08") [ 115 "-host ${stdenv.hostPlatform.config}" 116 "-target ${stdenv.targetPlatform.config}" 117 ] 118 ++ optional noNakedPointers (flags "--disable-naked-pointers" "-no-naked-pointers"); 119 dontAddStaticConfigureFlags = lib.versionOlder version "4.08"; 120 121 # on aarch64-darwin using --host and --target causes the build to invoke 122 # `aarch64-apple-darwin-clang` while using assembler. However, such binary 123 # does not exist. So, disable these configure flags on `aarch64-darwin`. 124 # See #144785 for details. 125 configurePlatforms = 126 lib.optionals 127 ( 128 lib.versionAtLeast version "4.08" 129 && !(stdenv.hostPlatform.isDarwin && stdenv.hostPlatform.isAarch64) 130 ) 131 [ 132 "host" 133 "target" 134 ]; 135 # x86_64-unknown-linux-musl-ld: -r and -pie may not be used together 136 hardeningDisable = 137 lib.optional (lib.versionAtLeast version "4.09" && stdenv.hostPlatform.isMusl) "pie" 138 ++ lib.optional (lib.versionAtLeast version "5.0" && stdenv.cc.isClang) "strictoverflow" 139 ++ lib.optionals (args ? hardeningDisable) args.hardeningDisable; 140 141 # Older versions have some race: 142 # cp: cannot stat 'boot/ocamlrun': No such file or directory 143 # make[2]: *** [Makefile:199: backup] Error 1 144 enableParallelBuilding = lib.versionAtLeast version "4.08"; 145 146 # Workaround missing dependencies for install parallelism: 147 # install: target '...-ocaml-4.14.0/lib/ocaml/threads': No such file or directory 148 # make[1]: *** [Makefile:140: installopt] Error 1 149 enableParallelInstalling = false; 150 151 # Workaround lack of parallelism support among top-level targets: 152 # we place nixpkgs-specific targets to a separate file and set 153 # sequential order among them as a single rule. 154 makefile = ./Makefile.nixpkgs; 155 buildFlags = 156 if useNativeCompilers then 157 [ 158 (if lib.versionOlder version "5.2" then "nixpkgs_world_bootstrap_world_opt" else "defaultentry") 159 ] 160 else 161 [ "nixpkgs_world" ]; 162 buildInputs = 163 optional (lib.versionOlder version "4.07") ncurses 164 ++ optionals useX11 [ 165 libX11 166 xorgproto 167 ]; 168 depsBuildBuild = lib.optionals (!stdenv.hostPlatform.isDarwin) [ binutils ]; 169 propagatedBuildInputs = optional spaceTimeSupport libunwind; 170 installTargets = [ "install" ] ++ optional useNativeCompilers "installopt"; 171 preConfigure = 172 optionalString (lib.versionOlder version "4.04") '' 173 CAT=$(type -tp cat) 174 sed -e "s@/bin/cat@$CAT@" -i config/auto-aux/sharpbang 175 '' 176 + optionalString (stdenv.hostPlatform.isDarwin) '' 177 # Do what upstream does by default now: https://github.com/ocaml/ocaml/pull/10176 178 # This is required for aarch64-darwin, everything else works as is. 179 AS="${stdenv.cc}/bin/cc -c" ASPP="${stdenv.cc}/bin/cc -c" 180 '' 181 + optionalString (lib.versionOlder version "4.08" && stdenv.hostPlatform.isStatic) '' 182 configureFlagsArray+=("-cc" "$CC" "-as" "$AS" "-partialld" "$LD -r") 183 ''; 184 postBuild = '' 185 mkdir -p $out/include 186 ln -sv $out/lib/ocaml/caml $out/include/caml 187 ''; 188 189 passthru = { 190 nativeCompilers = useNativeCompilers; 191 }; 192 193 meta = with lib; { 194 homepage = "https://ocaml.org/"; 195 branch = versionNoPatch; 196 license = with licenses; [ 197 qpl # compiler 198 lgpl2 # library 199 ]; 200 description = "OCaml is an industrial-strength programming language supporting functional, imperative and object-oriented styles"; 201 202 longDescription = '' 203 OCaml is a general purpose programming language with an emphasis on expressiveness and safety. Developed for more than 20 years at Inria by a group of leading researchers, it has an advanced type system that helps catch your mistakes without getting in your way. It's used in environments where a single mistake can cost millions and speed matters, is supported by an active community, and has a rich set of libraries and development tools. It's widely used in teaching for its power and simplicity. 204 205 Strengths: 206 * A powerful type system, equipped with parametric polymorphism and type inference. For instance, the type of a collection can be parameterized by the type of its elements. This allows defining some operations over a collection independently of the type of its elements: sorting an array is one example. Furthermore, type inference allows defining such operations without having to explicitly provide the type of their parameters and result. 207 * User-definable algebraic data types and pattern-matching. New algebraic data types can be defined as combinations of records and sums. Functions that operate over such data structures can then be defined by pattern matching, a generalized form of the well-known switch statement, which offers a clean and elegant way of simultaneously examining and naming data. 208 * Automatic memory management, thanks to a fast, unobtrusive, incremental garbage collector. 209 * Separate compilation of standalone applications. Portable bytecode compilers allow creating stand-alone applications out of Caml Light or OCaml programs. A foreign function interface allows OCaml code to interoperate with C code when necessary. Interactive use of OCaml is also supported via a read-evaluate-print loop. 210 211 In addition, OCaml features: 212 * A sophisticated module system, which allows organizing modules hierarchically and parameterizing a module over a number of other modules. 213 * An expressive object-oriented layer, featuring multiple inheritance, parametric and virtual classes. 214 * Efficient native code compilers. In addition to its bytecode compiler, OCaml offers a compiler that produces efficient machine code for many architectures. 215 216 Learn more at: https://ocaml.org/learn/description.html 217 ''; 218 219 platforms = with platforms; linux ++ darwin; 220 broken = 221 stdenv.hostPlatform.isAarch64 222 && lib.versionOlder version (if stdenv.hostPlatform.isDarwin then "4.10" else "4.02"); 223 }; 224 225 } 226)