[Nix-dev] "cross-compile" to non-standard nix-store location

Andreas Herrmann andreash87 at gmx.ch
Tue Sep 9 11:46:00 CEST 2014


Hi,

I'm using nix in single user mode in a non-standard location (${HOME}/nix/store) on a CentOS host on which I don't have root-access, and which I don't want to flood with lots of build jobs. I'm looking for a good way to "cross-compile" binaries on my laptop (nix in single user mode in standard location /nix/store) which I can then export and install on the CentOS machine.

---

Here is my current approach (Thanks to another exchange on the mailing list a while ago). It works, but feels a bit hacky, is hard to automate, and doesn't offer hardware specific compiler flags:

I created a new user on my laptop, which has the same name, and home as my user on the CentOS machine. That user has its own nix installation, which was configured to use the non-standard store path. I open a login shell in that user's name, and use nix-build to build whatever package I want to install on the CentOS machine. Finally, I use nix-store export/import to install it.

---

Is there a way to skip the extra user on my laptop? I tried a cross-compilation configuration. However, it doesn't seem to pick up the non-standard nix-store location, and actually fails to compile gcc4.9.

Here is the cross-compile config:

    let
      pkgsFun = import <nixpkgs>;
      pkgsNoParams = pkgsFun { };
    in
    pkgsFun {
      crossSystem = {
        config = "i686-pc-linux";
        arch = "x86_64";
        libc = "glibc";
        withTLS = true;
        float = "hard";
        platform = pkgsNoParams.platforms.pc64 // {
          kernelMajor = "2.6";
        };
        gcc.arch = "corei7-avx";
      };
    
      config = pkgs: {
        packageOverrides = pkgs: {
          nix = pkgs.nix.override {
            storeDir = "/home/user/nix/store";
            stateDir = "/home/user/nix/store";
          };
        };
      };
    }


I had to apply the following patch to nixpkgs because the linker name was missing for this platform:

    diff --git a/pkgs/build-support/gcc-wrapper/default.nix b/pkgs/build-support/gcc-wrapper/default.nix
    index 8e8b0b9..9a014b7 100644
    --- a/pkgs/build-support/gcc-wrapper/default.nix
    +++ b/pkgs/build-support/gcc-wrapper/default.nix
    @@ -70,6 +70,7 @@ stdenv.mkDerivation {
           (if stdenv.cross.arch == "arm" then "ld-linux.so.3" else
            if stdenv.cross.arch == "mips" then "ld.so.1" else
            if stdenv.lib.hasSuffix "pc-gnu" stdenv.cross.config then "ld.so.1" else
    +       if stdenv.cross.arch == "x86_64" then "ld-linux-x86-64.so.2" else
            abort "don't know the name of the dynamic linker for this platform");
       };


When I try to build gcc4.9 with `nix-build -A gcc49.crossDrv beo.nix` then it fails with this message:

    checking for .preinit_array/.init_array/.fini_array support... no
    configure: error: Need linker with .init_array/.fini_array support.
    builder for `/nix/store/hfix8jkynaj5r32kavyg2n1r5mp38092-glibc-2.19-i686-pc-linux.drv' failed with exit code 1
    cannot build derivation `/nix/store/x3z0v3szgv4wd9icdbbwk2x6zhxky35m-gcc-wrapper-4.9.1-i686-pc-linux.drv': 1 dependencies couldn't be built
    error: build of `/nix/store/x3z0v3szgv4wd9icdbbwk2x6zhxky35m-gcc-wrapper-4.9.1-i686-pc-linux.drv' failed


It seems that something is wrong with this linker configuration.
And it doesn't seem to pick up the non-standard nix-store path, as this is only an override for the nix package.

---

What is the best way to achieve what I'm trying to do? Is there a way to avoid the extra user on my laptop?


Thanks!

Andreas 


More information about the nix-dev mailing list