summary refs log tree commit diff
path: root/pkgs/build-support/rust/lib/default.nix
blob: aa5ba14c1397b24211a8a2a2e14e682be8de04c0 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
{ lib }:

rec {
  # https://doc.rust-lang.org/reference/conditional-compilation.html#target_arch
  toTargetArch = platform:
    /**/ if platform ? rustc.platform then platform.rustc.platform.arch
    else if platform.isAarch32 then "arm"
    else if platform.isMips64  then "mips64"     # never add "el" suffix
    else if platform.isPower64 then "powerpc64"  # never add "le" suffix
    else platform.parsed.cpu.name;

  # https://doc.rust-lang.org/reference/conditional-compilation.html#target_os
  toTargetOs = platform:
    /**/ if platform ? rustc.platform then platform.rustc.platform.os or "none"
    else if platform.isDarwin then "macos"
    else platform.parsed.kernel.name;

  # https://doc.rust-lang.org/reference/conditional-compilation.html#target_family
  toTargetFamily = platform:
    if platform ? rustc.platform.target-family
    then
      (
        # Since https://github.com/rust-lang/rust/pull/84072
        # `target-family` is a list instead of single value.
        let
          f = platform.rustc.platform.target-family;
        in
        if builtins.isList f then f else [ f ]
      )
    else lib.optional platform.isUnix "unix"
      ++ lib.optional platform.isWindows "windows";

  # https://doc.rust-lang.org/reference/conditional-compilation.html#target_vendor
  toTargetVendor = platform: let
    inherit (platform.parsed) vendor;
  in platform.rustc.platform.vendor or {
    "w64" = "pc";
  }.${vendor.name} or vendor.name;

  # Returns the name of the rust target, even if it is custom. Adjustments are
  # because rust has slightly different naming conventions than we do.
  toRustTarget = platform: let
    inherit (platform.parsed) cpu kernel abi;
    cpu_ = platform.rustc.platform.arch or {
      "armv7a" = "armv7";
      "armv7l" = "armv7";
      "armv6l" = "arm";
      "armv5tel" = "armv5te";
      "riscv64" = "riscv64gc";
    }.${cpu.name} or cpu.name;
    vendor_ = toTargetVendor platform;
  in platform.rustc.config
    or "${cpu_}-${vendor_}-${kernel.name}${lib.optionalString (abi.name != "unknown") "-${abi.name}"}";

  # Returns the name of the rust target if it is standard, or the json file
  # containing the custom target spec.
  toRustTargetSpec = platform:
    if platform ? rustc.platform
    then builtins.toFile (toRustTarget platform + ".json") (builtins.toJSON platform.rustc.platform)
    else toRustTarget platform;

  # Returns true if the target is no_std
  # https://github.com/rust-lang/rust/blob/2e44c17c12cec45b6a682b1e53a04ac5b5fcc9d2/src/bootstrap/config.rs#L415-L421
  IsNoStdTarget = platform: let rustTarget = toRustTarget platform; in
    builtins.any (t: lib.hasInfix t rustTarget) ["-none" "nvptx" "switch" "-uefi"];
}