bcachefs-tools/flake.nix
Thomas Mühlbacher e47a5ce2bc fix(nix): allow msrv test to have warnings
It is otherwise inconvenient or maybe in other cases even impossible to
have clippy pass with both the current Rust version as well as the MSRV
Rust version. (e.g. `clippy::missing_transmute_annotations` is not yet
known to our current MSRV.)

Signed-off-by: Thomas Mühlbacher <tmuehlbacher@posteo.net>
Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev>
2025-03-31 20:29:39 -04:00

328 lines
9.8 KiB
Nix

{
description = "Userspace tools for bcachefs";
inputs = {
nixpkgs.url = "github:nixos/nixpkgs/nixos-unstable";
flake-parts.url = "github:hercules-ci/flake-parts";
treefmt-nix = {
url = "github:numtide/treefmt-nix";
inputs.nixpkgs.follows = "nixpkgs";
};
crane.url = "github:ipetkov/crane";
rust-overlay = {
url = "github:oxalica/rust-overlay";
inputs.nixpkgs.follows = "nixpkgs";
};
flake-compat = {
url = "github:edolstra/flake-compat";
flake = false;
};
nix-github-actions = {
url = "github:nix-community/nix-github-actions";
inputs.nixpkgs.follows = "nixpkgs";
};
};
outputs =
inputs@{
self,
nixpkgs,
flake-parts,
treefmt-nix,
crane,
rust-overlay,
flake-compat,
nix-github-actions,
}:
let
systems = nixpkgs.lib.filter (s: nixpkgs.lib.hasSuffix "-linux" s) nixpkgs.lib.systems.flakeExposed;
in
flake-parts.lib.mkFlake { inherit inputs; } {
imports = [ inputs.treefmt-nix.flakeModule ];
flake = {
githubActions = nix-github-actions.lib.mkGithubMatrix {
# github actions supports fewer architectures
checks = nixpkgs.lib.getAttrs [ "aarch64-linux" "x86_64-linux" ] self.checks;
};
};
inherit systems;
perSystem =
{
self',
config,
lib,
system,
...
}:
let
inherit (builtins) readFile split;
inherit (lib.lists) findFirst;
inherit (lib.strings) hasPrefix removePrefix substring;
pkgs = import nixpkgs {
inherit system;
overlays = [ (import rust-overlay) ];
};
cargoToml = builtins.fromTOML (builtins.readFile ./Cargo.toml);
rustfmtToml = builtins.fromTOML (builtins.readFile ./rustfmt.toml);
rev = self.shortRev or self.dirtyShortRev or (substring 0 8 self.lastModifiedDate);
makefileVersion = removePrefix "VERSION=" (
findFirst (line: hasPrefix "VERSION=" line) "VERSION=0.0.0" (split "\n" (readFile ./Makefile))
);
version = "${makefileVersion}+${rev}";
mkCommon =
{
crane,
pkgs,
rustVersion ? "latest",
# build time
buildPackages,
pkg-config,
rustPlatform,
stdenv,
# run time
keyutils,
libaio,
libsodium,
liburcu,
libuuid,
lz4,
udev,
zlib,
zstd,
}:
let
inherit (stdenv) cc hostPlatform;
craneLib = (crane.mkLib pkgs).overrideToolchain (
p: p.rust-bin.stable."${rustVersion}".minimal.override { extensions = [ "clippy" ]; }
);
args = {
inherit version;
src = self;
strictDeps = true;
env = {
PKG_CONFIG_SYSTEMD_SYSTEMDSYSTEMUNITDIR = "${placeholder "out"}/lib/systemd/system";
PKG_CONFIG_UDEV_UDEVDIR = "${placeholder "out"}/lib/udev";
CARGO_BUILD_TARGET = hostPlatform.rust.rustcTargetSpec;
"CARGO_TARGET_${hostPlatform.rust.cargoEnvVarTarget}_LINKER" = "${cc.targetPrefix}cc";
HOST_CC = "${cc.nativePrefix}cc";
TARGET_CC = "${cc.targetPrefix}cc";
};
makeFlags = [
"INITRAMFS_DIR=${placeholder "out"}/etc/initramfs-tools"
"PREFIX=${placeholder "out"}"
"VERSION=${version}"
];
dontStrip = true;
depsBuildBuild = [
buildPackages.stdenv.cc
];
nativeBuildInputs = [
pkg-config
rustPlatform.bindgenHook
];
buildInputs = [
keyutils
libaio
libsodium
liburcu
libuuid
lz4
udev
zlib
zstd
];
meta = {
description = "Userspace tools for bcachefs";
license = lib.licenses.gpl2Only;
mainProgram = "bcachefs";
};
};
cargoArtifacts = craneLib.buildDepsOnly args;
in
{
inherit args cargoArtifacts craneLib;
};
common = pkgs.callPackage mkCommon { inherit crane; };
mkPackage =
{ common, name }:
common.craneLib.buildPackage (
common.args
// {
inherit (common) cargoArtifacts;
pname = name;
enableParallelBuilding = true;
buildPhaseCargoCommand = ''
make ''${enableParallelBuilding:+-j''${NIX_BUILD_CORES}} $makeFlags
'';
doNotPostBuildInstallCargoBinaries = true;
installPhaseCommand = ''
make ''${enableParallelBuilding:+-j''${NIX_BUILD_CORES}} $makeFlags install
'';
doInstallCheck = true;
installCheckPhase = ''
runHook preInstallCheck
test "$($out/bin/bcachefs version)" = "${version}"
runHook postInstallCheck
'';
}
);
mkPackages =
name: systems:
let
packagesForSystem =
crossSystem:
let
localSystem = system;
pkgs' = import nixpkgs {
inherit crossSystem localSystem;
overlays = [ (import rust-overlay) ];
};
common = pkgs'.callPackage mkCommon { inherit crane; };
package = pkgs'.callPackage mkPackage { inherit common name; };
packageFuse = package.overrideAttrs (
final: prev: {
makeFlags = prev.makeFlags ++ [ "BCACHEFS_FUSE=1" ];
buildInputs = prev.buildInputs ++ [ pkgs'.fuse3 ];
}
);
in
[
(lib.nameValuePair "${name}-${crossSystem}" package)
(lib.nameValuePair "${name}-fuse-${crossSystem}" packageFuse)
];
in
lib.listToAttrs (lib.flatten (map packagesForSystem systems));
in
{
packages =
let
inherit (cargoToml.package) name;
in
(mkPackages name systems)
// {
${name} = config.packages."${name}-${system}";
"${name}-fuse" = config.packages."${name}-fuse-${system}";
default = config.packages.${name};
};
checks = {
inherit (config.packages)
bcachefs-tools
bcachefs-tools-fuse
bcachefs-tools-fuse-i686-linux
;
cargo-clippy = common.craneLib.cargoClippy (
common.args
// {
inherit (common) cargoArtifacts;
cargoClippyExtraArgs = "--all-targets --all-features -- --deny warnings";
}
);
# we have to build our own `craneLib.cargoTest`
cargo-test = common.craneLib.mkCargoDerivation (
common.args
// {
inherit (common) cargoArtifacts;
doCheck = true;
enableParallelChecking = true;
pnameSuffix = "-test";
buildPhaseCargoCommand = "";
checkPhaseCargoCommand = ''
make ''${enableParallelChecking:+-j''${NIX_BUILD_CORES}} $makeFlags libbcachefs.a
cargo test --profile release -- --nocapture
'';
}
);
# cargo clippy with the current minimum supported rust version
# according to Cargo.toml
msrv =
let
rustVersion = cargoToml.package.rust-version;
common = pkgs.callPackage mkCommon { inherit crane rustVersion; };
in
common.craneLib.cargoClippy (
common.args
// {
pname = "msrv";
inherit (common) cargoArtifacts;
cargoClippyExtraArgs = "--all-targets --all-features";
}
);
};
devShells.default = pkgs.mkShell {
inputsFrom = [
config.packages.default
config.treefmt.build.devShell
];
# here go packages that aren't required for builds but are used for
# development, and might need to be version matched with build
# dependencies (e.g. clippy or rust-analyzer).
packages = with pkgs; [
bear
cargo-audit
cargo-outdated
clang-tools
(rust-bin.stable.latest.minimal.override {
extensions = [
"rust-analyzer"
"rust-src"
];
})
];
};
treefmt.config = {
projectRootFile = "flake.nix";
flakeCheck = false;
programs = {
nixfmt.enable = true;
rustfmt.edition = rustfmtToml.edition;
rustfmt.enable = true;
rustfmt.package = pkgs.rust-bin.selectLatestNightlyWith (toolchain: toolchain.rustfmt);
};
};
};
};
}