From 6980e6b35aacccd4e75a76a384f9dec30f31fa55 Mon Sep 17 00:00:00 2001 From: Adam Joseph Date: Wed, 28 Jun 2023 23:49:38 -0700 Subject: [PATCH] lib.systems: introduce hasSharedLibraries This commit adds `hasSharedLibraries` to `lib.systems`. We need `plat.hasSharedLibraries` in order to know whether or not to expect `gcc` (and many other tools) to emit shared libraries (like `libgcc_s.so`). Many of the GNU build scripts are smart enough that if you configure them with `--enable-shared` on a platform (such as `arm-none-eabi`) that doesn't support dynamic linking, they will simply skip the shared libraries instead of aborting the `configurePhase`. Unfortunately the missing shared libraries in the final build product cause very hard-to-troubleshoot problems later on. The alternative to introducing `hasSharedLibraries` would be to set `isStatic` in these situations. However doing so causes `make-derivation.nix` to insert `-static` between the `pname` and `hostPlatform` suffix, which is undesirable. If at some point in the future we eliminate the `-static` suffix, then `hasSharedLibraries` can be made equal to `!isStatic`. --- lib/systems/default.nix | 21 ++++++++++++++++++++- 1 file changed, 20 insertions(+), 1 deletion(-) diff --git a/lib/systems/default.nix b/lib/systems/default.nix index 78ccd50ba79a..a3462d2d424b 100644 --- a/lib/systems/default.nix +++ b/lib/systems/default.nix @@ -86,7 +86,7 @@ rec { # choice. else "bfd"; extensions = rec { - sharedLibrary = + sharedLibrary = assert final.hasSharedLibraries; /**/ if final.isDarwin then ".dylib" else if final.isWindows then ".dll" else ".so"; @@ -132,6 +132,25 @@ rec { # uname -r release = null; }; + + # It is important that hasSharedLibraries==false when the platform has no + # dynamic library loader. Various tools (including the gcc build system) + # have knowledge of which platforms are incapable of dynamic linking, and + # will still build on/for those platforms with --enable-shared, but simply + # omit any `.so` build products such as libgcc_s.so. When that happens, + # it causes hard-to-troubleshoot build failures. + hasSharedLibraries = with final; + (isAndroid || isGnu || isMusl # Linux (allows multiple libcs) + || isDarwin || isSunOS || isOpenBSD || isFreeBSD || isNetBSD # BSDs + || isCygwin || isMinGW # Windows + ) && !isStatic; + + # The difference between `isStatic` and `hasSharedLibraries` is mainly the + # addition of the `staticMarker` (see make-derivation.nix). Some + # platforms, like embedded machines without a libc (e.g. arm-none-eabi) + # don't support dynamic linking, but don't get the `staticMarker`. + # `pkgsStatic` sets `isStatic=true`, so `pkgsStatic.hostPlatform` always + # has the `staticMarker`. isStatic = final.isWasm || final.isRedox; # Just a guess, based on `system`