2affd455a4
This commit allows `gccCrossStageStatic` to build dynamically-linked
libraries. Since is no longer restricted to building static
libraries its name is no longer appropriate, and this commit also
renames it to the more-accurate `gccWithoutTargetLibc`.
By default, you can't build a gcc that knows how to create dynamic
libraries unless you have already built the targetPlatform libc.
Because of this, our gcc cross-compiler is built in two stages:
1. Build a cross-compiler (gccCrossStageStatic) that can build
only static libraries.
2. Use gccCrossStageStatic to compile the targetPlatform libc.
3. Use the targetPlatform libc to build a fully-capable cross
compiler.
You might notice that this pattern looks very similar to what we do
with `xgcc` in the stdenv bootstrap. Indeed it is! I would like to
work towards getting the existing stdenv bootstrap to handle cross
compilers as well. However we don't want to cripple `stdenv.xgcc`
by taking away its ability to build dynamic libraries.
It turns out that the only thing gcc needs the targetPlatform libc
for is to emit a DT_NEEDED for `-lc` into `libgcc.so`. That's it!
And since we don't use `gccCrossStageStatic` to build anything other
than libc, it's safe to omit the `DT_NEEDED` because that `libgcc`
will never be loaded by anything other than `libc`. So `libc` will
already be in the process's address space.
Other people have noticed this; crosstool-ng has been using this
approach for a very long time:
36ad0b17a7/scripts/build/cc/gcc.sh (L638-L640)
51 lines
1.2 KiB
Nix
51 lines
1.2 KiB
Nix
{ lib, stdenv, buildPackages
|
|
, newScope, overrideCC, crossLibcStdenv, libcCross
|
|
}:
|
|
|
|
lib.makeScope newScope (self: with self; {
|
|
|
|
cygwinSetup = callPackage ./cygwin-setup { };
|
|
|
|
jom = callPackage ./jom { };
|
|
|
|
w32api = callPackage ./w32api { };
|
|
|
|
mingwrt = callPackage ./mingwrt { };
|
|
mingw_runtime = mingwrt;
|
|
|
|
mingw_w64 = callPackage ./mingw-w64 {
|
|
stdenv = crossLibcStdenv;
|
|
};
|
|
|
|
crossThreadsStdenv = overrideCC crossLibcStdenv
|
|
(if stdenv.hostPlatform.useLLVM or false
|
|
then buildPackages.llvmPackages_8.clangNoLibcxx
|
|
else buildPackages.gccWithoutTargetLibc.override (old: {
|
|
bintools = old.bintools.override {
|
|
libc = libcCross;
|
|
};
|
|
libc = libcCross;
|
|
}));
|
|
|
|
mingw_w64_headers = callPackage ./mingw-w64/headers.nix { };
|
|
|
|
mingw_w64_pthreads = callPackage ./mingw-w64/pthreads.nix {
|
|
stdenv = crossThreadsStdenv;
|
|
};
|
|
|
|
mcfgthreads_pre_gcc_13 = callPackage ./mcfgthreads/pre_gcc_13.nix {
|
|
stdenv = crossThreadsStdenv;
|
|
};
|
|
|
|
mcfgthreads = callPackage ./mcfgthreads {
|
|
stdenv = crossThreadsStdenv;
|
|
};
|
|
|
|
npiperelay = callPackage ./npiperelay { };
|
|
|
|
pthreads = callPackage ./pthread-w32 { };
|
|
|
|
wxMSW = callPackage ./wxMSW-2.8 { };
|
|
|
|
libgnurx = callPackage ./libgnurx { };
|
|
})
|