about summary refs log tree commit diff
path: root/pkgs/os-specific/linux/kernel/manual-config.nix
diff options
context:
space:
mode:
Diffstat (limited to 'pkgs/os-specific/linux/kernel/manual-config.nix')
-rw-r--r--pkgs/os-specific/linux/kernel/manual-config.nix252
1 files changed, 131 insertions, 121 deletions
diff --git a/pkgs/os-specific/linux/kernel/manual-config.nix b/pkgs/os-specific/linux/kernel/manual-config.nix
index 3219ef0b002b..9c82aea41aa6 100644
--- a/pkgs/os-specific/linux/kernel/manual-config.nix
+++ b/pkgs/os-specific/linux/kernel/manual-config.nix
@@ -19,110 +19,153 @@ in {
   src,
   # Any patches
   kernelPatches ? [],
-  # The kernel .config file
+  # Patches for native compiling only
+  nativeKernelPatches ? [],
+  # Patches for cross compiling only
+  crossKernelPatches ? [],
+  # The native kernel .config file
   configfile,
+  # The cross kernel .config file
+  crossConfigfile ? configfile,
   # Manually specified nixexpr representing the config
   # If unspecified, this will be autodetected from the .config
   config ? stdenv.lib.optionalAttrs allowImportFromDerivation (readConfig configfile),
+  # Cross-compiling config
+  crossConfig ? if allowImportFromDerivation then (readConfig crossConfigfile) else config,
   # Whether to utilize the controversial import-from-derivation feature to parse the config
   allowImportFromDerivation ? false
 }:
 
-let config_ = config; in
-
 let
   inherit (stdenv.lib)
-    hasAttr getAttr optionalAttrs optional optionalString maintainers platforms;
-
-  config = let attrName = attr: "CONFIG_" + attr; in {
-    isSet = attr: hasAttr (attrName attr) config;
-
-    getValue = attr: if config.isSet attr then getAttr (attrName attr) config else null;
-
-    isYes = attr: (config.getValue attr) == "y";
-
-    isNo = attr: (config.getValue attr) == "n";
-
-    isModule = attr: (config.getValue attr) == "m";
-
-    isEnabled = attr: (config.isModule attr) || (config.isYes attr);
-
-    isDisabled = attr: (!(config.isSet attr)) || (config.isNo attr);
-  } // config_;
+    hasAttr getAttr optional optionalString maintainers platforms;
 
   installkernel = writeTextFile { name = "installkernel"; executable=true; text = ''
     #!${stdenv.shell} -e
     mkdir -p $4
     cp -av $2 $4
     cp -av $3 $4
-  '';};
-
-  isModular = config.isYes "MODULES";
-
-  installsFirmware = (config.isEnabled "FW_LOADER") &&
-    (isModular || (config.isDisabled "FIRMWARE_IN_KERNEL"));
+  ''; };
 
   commonMakeFlags = [
     "O=$(buildRoot)"
   ];
 
-  # Some image types need special install targets (e.g. uImage is installed with make uinstall)
-  installTarget = target: [ (if target == "uImage" then "uinstall" else "install") ];
-
-  sourceRoot = stdenv.mkDerivation {
-    name = "linux-source-${version}";
-
-    inherit src;
-
-    patches = map (p: p.patch) kernelPatches;
-
-    phases = [ "unpackPhase" "patchPhase" "installPhase" ]; 
-
-    prePatch = ''
-      for mf in $(find -name Makefile -o -name Makefile.include -o -name install.sh); do
-          echo "stripping FHS paths in \`$mf'..."
-          sed -i "$mf" -e 's|/usr/bin/||g ; s|/bin/||g ; s|/sbin/||g'
-      done
-      sed -i Makefile -e 's|= depmod|= ${kmod}/sbin/depmod|'
-      # Patch kconfig to print "###" after every question so that
-      # generate-config.pl from the generic builder can answer them.
-      # This only affects oldaskconfig.
-      sed -e '/fflush(stdout);/i\printf("###");' -i scripts/kconfig/conf.c
-    '';
+  drvAttrs = config_: platform: kernelPatches: configfile:
+    let
+      config = let attrName = attr: "CONFIG_" + attr; in {
+        isSet = attr: hasAttr (attrName attr) config;
 
-    installPhase = ''
-      cd ..
-      mv $sourceRoot $out
-    '';
-  };
+        getValue = attr: if config.isSet attr then getAttr (attrName attr) config else null;
+
+        isYes = attr: (config.getValue attr) == "y";
+
+        isNo = attr: (config.getValue attr) == "n";
+
+        isModule = attr: (config.getValue attr) == "m";
+
+        isEnabled = attr: (config.isModule attr) || (config.isYes attr);
+
+        isDisabled = attr: (!(config.isSet attr)) || (config.isNo attr);
+      } // config_;
+
+      isModular = config.isYes "MODULES";
+
+      installsFirmware = (config.isEnabled "FW_LOADER") &&
+        (isModular || (config.isDisabled "FIRMWARE_IN_KERNEL"));
+
+      sourceRoot = stdenv.mkDerivation {
+        name = "linux-source-${version}";
+
+        inherit src;
+
+        patches = map (p: p.patch) kernelPatches;
+
+        phases = [ "unpackPhase" "patchPhase" "installPhase" ];
+
+        prePatch = ''
+          for mf in $(find -name Makefile -o -name Makefile.include -o -name install.sh); do
+              echo "stripping FHS paths in \`$mf'..."
+              sed -i "$mf" -e 's|/usr/bin/||g ; s|/bin/||g ; s|/sbin/||g'
+          done
+
+          sed -i Makefile -e 's|= depmod|= ${kmod}/sbin/depmod|'
+
+          # Patch kconfig to print "###" after every question so that
+          # generate-config.pl from the generic builder can answer them.
+          # This only affects oldaskconfig.
+          sed -e '/fflush(stdout);/i\printf("###");' -i scripts/kconfig/conf.c
+        '';
+
+        installPhase = ''
+          cd ..
+          mv $sourceRoot $out
+        '';
+      };
+    in {
+      outputs = if isModular then [ "out" "dev" ] else null;
+
+      passthru = {
+        inherit version modDirVersion config kernelPatches src;
+      };
+
+      inherit sourceRoot;
+
+      unpackPhase = ''
+        mkdir build
+        export buildRoot="$(pwd)/build"
+        cd ${sourceRoot}
+      '';
+
+      configurePhase = ''
+        runHook preConfigure
+        ln -sv ${configfile} $buildRoot/.config
+        make $makeFlags "''${makeFlagsArray[@]}" oldconfig
+        runHook postConfigure
+      '';
+
+      buildFlags = [ stdenv.platform.kernelTarget ] ++ optional isModular "modules";
+
+      installFlags = [
+        "INSTALLKERNEL=${installkernel}"
+        "INSTALL_PATH=$(out)"
+      ] ++ (optional isModular "INSTALL_MOD_PATH=$(out)")
+      ++ optional installsFirmware "INSTALL_FW_PATH=$(out)/lib/firmware";
+
+      # Some image types need special install targets (e.g. uImage is installed with make uinstall)
+      installTargets = [ (if platform.kernelTarget == "uImage" then "uinstall" else "install") ];
+
+      postInstall = optionalString installsFirmware ''
+        mkdir -p $out/lib/firmware
+      '' + (if isModular then ''
+        make modules_install $makeFlags "''${makeFlagsArray[@]}" \
+          $installFlags "''${installFlagsArray[@]}"
+        unlink $out/lib/modules/${modDirVersion}/build
+        mkdir -p $dev/lib/modules/${modDirVersion}
+        mv $out/lib/modules/${modDirVersion}/source $dev/lib/modules/${modDirVersion}/source
+        mv $buildRoot $dev/lib/modules/${modDirVersion}/build
+      '' else optionalString installsFirmware ''
+        make firmware_install $makeFlags "''${makeFlagsArray[@]}" \
+          $installFlags "''${installFlagsArray[@]}"
+      '');
+
+      postFixup = if isModular then ''
+        if [ -z "$dontStrip" ]; then
+            find $out -name "*.ko" -print0 | xargs -0 -r ''${crossConfig+$crossConfig-}strip -S
+            # Remove all references to the source directory to avoid unneeded
+            # runtime dependencies
+            find $out -name "*.ko" -print0 | xargs -0 -r sed -i \
+              "s|${sourceRoot}|$NIX_STORE/eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee-${sourceRoot.name}|g"
+        fi
+      '' else null;
+    };
 in
 
-stdenv.mkDerivation {
+stdenv.mkDerivation ((drvAttrs config stdenv.platform (kernelPatches ++ nativeKernelPatches) configfile) // {
   name = "linux-${version}";
 
   enableParallelBuilding = true;
 
-  outputs = if isModular then [ "out" "dev" ] else null;
-
-  passthru = {
-    inherit version modDirVersion config kernelPatches src;
-  };
-
-  inherit sourceRoot;
-
-  unpackPhase = ''
-    mkdir build
-    export buildRoot="$(pwd)/build"
-    cd ${sourceRoot}
-  '';
-
-  configurePhase = ''
-    runHook preConfigure
-    ln -sv ${configfile} $buildRoot/.config
-    make $makeFlags "''${makeFlagsArray[@]}" oldconfig
-    runHook postConfigure
-  '';
-
   nativeBuildInputs = [ perl bc nettools ] ++ optional (stdenv.platform.uboot != null)
     (ubootChooser stdenv.platform.uboot);
 
@@ -130,53 +173,20 @@ stdenv.mkDerivation {
     "ARCH=${stdenv.platform.kernelArch}"
   ];
 
-  buildFlags = [ stdenv.platform.kernelTarget ] ++ optional isModular "modules";
-
-  installFlags = [
-    "INSTALLKERNEL=${installkernel}"
-    "INSTALL_PATH=$(out)"
-  ] ++ (optional isModular "INSTALL_MOD_PATH=$(out)")
-  ++ optional installsFirmware "INSTALL_FW_PATH=$(out)/lib/firmware";
-
-  installTargets = installTarget stdenv.platform.kernelTarget;
-
   crossAttrs = let cp = stdenv.cross.platform; in {
-    buildFlags = [ cp.kernelTarget ] ++ optional isModular "modules";
-
-    makeFlags = commonMakeFlags ++ [
-      "ARCH=${cp.kernelArch}"
-      "CROSS_COMPILE=$(crossConfig)-"
-    ];
-
-    installTargets = installTarget cp.kernelTarget;
-
-    buildInputs = optional (cp.uboot != null) (ubootChooser cp.uboot).crossDrv;
+    (drvAttrs crossConfig cp (kernelPatches ++ crossKernelPatches) crossConfigfile) // {
+      makeFlags = commonMakeFlags ++ [
+        "ARCH=${cp.kernelArch}"
+        "CROSS_COMPILE=$(crossConfig)-"
+      ];
+
+      # !!! uboot has messed up cross-compiling, nativeDrv builds arm tools on x86,
+      # crossDrv builds x86 tools on x86 (but arm uboot). If this is fixed, uboot
+      # can just go into buildInputs (but not nativeBuildInputs since cp.uboot
+      # may be different from stdenv.platform.uboot)
+      buildInputs = optional (cp.uboot != null) (ubootChooser cp.uboot).crossDrv;
   };
 
-  postInstall = optionalString installsFirmware ''
-    mkdir -p $out/lib/firmware
-  '' + (if isModular then ''
-    make modules_install $makeFlags "''${makeFlagsArray[@]}" \
-      $installFlags "''${installFlagsArray[@]}"
-    unlink $out/lib/modules/${modDirVersion}/build
-    mkdir -p $dev/lib/modules/${modDirVersion}
-    mv $out/lib/modules/${modDirVersion}/source $dev/lib/modules/${modDirVersion}/source
-    mv $buildRoot $dev/lib/modules/${modDirVersion}/build
-  '' else optionalString installsFirmware ''
-    make firmware_install $makeFlags "''${makeFlagsArray[@]}" \
-      $installFlags "''${installFlagsArray[@]}"
-  '');
-
-  postFixup = if isModular then ''
-    if [ -z "$dontStrip" ]; then
-        find $out -name "*.ko" -print0 | xargs -0 -r ''${crossConfig+$crossConfig-}strip -S
-        # Remove all references to the source directory to avoid unneeded
-        # runtime dependencies
-        find $out -name "*.ko" -print0 | xargs -0 -r sed -i \
-          "s|${sourceRoot}|$NIX_STORE/eeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee-${sourceRoot.name}|g"
-    fi
-  '' else null;
-
   meta = {
     description = "The Linux kernel";
     license = "GPLv2";
@@ -186,4 +196,4 @@ stdenv.mkDerivation {
     ];
     platforms = platforms.linux;
   };
-}
+})