NixOS / nixpkgs

Nix Packages collection & NixOS
MIT License
18.19k stars 14.2k forks source link

Packaging up CLING (or dealing with multiple external sources in a single package) #29661

Closed CMCDragonkai closed 3 years ago

CMCDragonkai commented 7 years ago

If you were to try to package up cling independent of the root framework, the manual instructions listed here: https://root.cern.ch/cling-build-instructions indicate multiple git repositories that must be fetched and composed together imperatively.

How would one write a nix expression to do this?

One way might be to write multiple nix expressions, one for each src url. With the final one imperatively doing symlinks to construct the expected FS structure, and then running cmake. But is there a way to bring in multiple external sources in a single nix expression? How would this relate to the stdenv.mkDerivation src attribute.

copumpkin commented 7 years ago

I thought mkDerivation will optionally accept a srcs attribute which is a list that gets treated like src.

CMCDragonkai commented 7 years ago

Ok, @copumpkin what's your opinion on building up the expected filesystem tree for building cling?

dtzWill commented 7 years ago

I don't think the default unpackPhase will neatly handle creation of multiple source directories.

Usually, at least what I've seen, these things are handled with a custom unpackPhase that builds up the source tree as expected.

An example of this can be seen in the LLVM expression:

https://github.com/NixOS/nixpkgs/blob/master/pkgs/development/compilers/llvm/5/llvm.nix#L33

Handling this directly would be rather neat, but AFAIK such infrastructure doesn't already exist.


I'm imagining something like the following would be pretty neat:

srcs = {
  llvm = {
    src = fetchurl { ... };
    projects.compiler-rt = fetchurl { ... };
};

(with hopefully better syntax for cleanly expressing this sort of thing)

CMCDragonkai commented 7 years ago

Another thing is that specifying llvm as a dependency for a cling expression doesn't bring in the llvm source. Only the headers and shared objects. I wonder if there's plans to address "source" packages.

However it looks like cling uses it down llvm fork and branch with special patches for cling.

leira commented 6 years ago

What's going on with the packaging of cling? I still don't see a cling package in nixpkgs.

@CMCDragonkai, have you make it work? Do you mind sharing the nix file?

CMCDragonkai commented 6 years ago

Nope haven't worked on it. Can you?

scalavision commented 6 years ago

Maybe this blog could give you some pointers on how to make it work?

http://sandervanderburg.blogspot.com/2014/07/

thomasjm commented 5 years ago

Hi all -- I think I've got it working here, anyone want to try? https://github.com/codedownio/nixpkgs/commit/4c43464a5acbba7e61b475718b64a7365cdea906

Seems to work, I was able to run ./cling '#include <stdio.h>' 'printf("Hello World!\n")'.

It's sort of regrettable that we have to build a special version of clang/llvm rather than use the one in Nix already, but since cling uses its own special patched branch of these I guess there's nothing for it...

MMesch commented 5 years ago

just tried it and it works fine. I added a few compiler flags and I was able to build the xeus-cling jupyter kernel with it. It takes really long to build though, about 2h on my laptop. The result is here: https://github.com/tweag/jupyterWith . The cling-related files are here: https://github.com/tweag/jupyterWith/tree/master/kernels/xeus-cling .

stephane-rolland commented 5 years ago

Unfortunately the proposed solution does not seem to work for me.

First, for some reasons beyond my knowledge of nix language, with nix-build, I need to modify the cling.nix file you proposed: The first line I have to change it to with import <nixpkgs> {};

Then, although the build seem to succeed, when I launch $ cling, I get a warning at startup and a segmentation fault when running code:

./result/bin/cling

In file included from input_line_1:1:
In file included from /nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/lib/gcc/x86_64-unknown-linux-gnu/7.3.0/../../../../include/c++/7.3.0/new:39:
In file included from /nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/lib/gcc/x86_64-unknown-linux-gnu/7.3.0/../../../../include/c++/7.3.0/x86_64-unknown-linux-gnu/bits/c++config.h:533:
/nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/lib/gcc/x86_64-unknown-linux-gnu/7.3.0/../../../../include/c++/7.3.0/x86_64-unknown-linux-gnu/bits/os_defines.h:39:10: fatal error: 'features.h' file not found
#include <features.h>
^~~~~~~~~~~~

****************** CLING ******************
* Type C++ code and press enter to run it *
*             Type .q to exit             *
*******************************************
[cling]$ int i=4;
[cling]$ i
#0 0x0000000000ae4c7a llvm::sys::PrintStackTrace(llvm::raw_ostream&) (./result/bin/cling+0xae4c7a)
#1 0x0000000000ae2b46 llvm::sys::RunSignalHandlers() (./result/bin/cling+0xae2b46)
#2 0x0000000000ae2c8c SignalHandler(int) (./result/bin/cling+0xae2c8c)
#3 0x00007f8350df8c50 __restore_rt (/nix/store/7gx4kiv5m0i7d7qkixq2cwzbr10lvxwc-glibc-2.27/lib/libc.so.6+0x34c50)
#4 0x0000000003425730 clang::Sema::LookupQualifiedName(clang::LookupResult&, clang::DeclContext*, bool) [clone .part.1035] (./result/bin/cling+0x3425730)
#5 0x0000000000a764d0 cling::ValueExtractionSynthesizer::FindAndCacheRuntimeDecls() (./result/bin/cling+0xa764d0)
#6 0x0000000000a775f5 cling::ValueExtractionSynthesizer::SynthesizeSVRInit(clang::Expr*) (./result/bin/cling+0xa775f5)
#7 0x0000000000a7811a cling::ValueExtractionSynthesizer::Transform(clang::Decl*) (./result/bin/cling+0xa7811a)
#8 0x00000000009ee6d6 cling::DeclCollector::TransformDecl(clang::Decl*) const (./result/bin/cling+0x9ee6d6)
#9 0x00000000009ee7cf cling::DeclCollector::Transform(clang::DeclGroupRef&) (./result/bin/cling+0x9ee7cf)
#10 0x00000000009ee981 cling::DeclCollector::HandleTopLevelDecl(clang::DeclGroupRef) (./result/bin/cling+0x9ee981)
#11 0x0000000000a422ac cling::IncrementalParser::ParseInternal(llvm::StringRef) (./result/bin/cling+0xa422ac)
#12 0x0000000000a4531c cling::IncrementalParser::Compile(llvm::StringRef, cling::CompilationOptions const&) (./result/bin/cling+0xa4531c)
#13 0x0000000000a4a61e cling::Interpreter::EvaluateInternal(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, cling::CompilationOptions, cling::Value*, cling::Transaction**, unsigned long) (./result/bin/cling+0xa4a61e)
#14 0x0000000000a4af57 cling::Interpreter::process(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, cling::Value*, cling::Transaction**, bool) (./result/bin/cling+0xa4af57)
#15 0x0000000000a939dd cling::MetaProcessor::process(llvm::StringRef, cling::Interpreter::CompilationResult&, cling::Value*, bool) (./result/bin/cling+0xa939dd)
#16 0x0000000000b0f507 cling::UserInterface::runInteractively(bool) (./result/bin/cling+0xb0f507)
#17 0x0000000000923189 main (./result/bin/cling+0x923189)
#18 0x00007f8350de5b8e __libc_start_main (/nix/store/7gx4kiv5m0i7d7qkixq2cwzbr10lvxwc-glibc-2.27/lib/libc.so.6+0x21b8e)
#19 0x000000000099683a _start (./result/bin/cling+0x99683a)
Stack dump:
0.      Program arguments: ./result/bin/cling
Segmentation fault

I get the same kind of access violations when launching the Hello World example you used. ./cling '#include <stdio.h>' 'printf("Hello World!\n")'.

When looking at the warning, it says it lacks the file <features.h> for including.

In my nix-store I do have this file, I am currently assuming it is the glibc-dev/include/features.h that is not reachable

./97mn9nbanzl8dm4gqza2d0jnzgi4zxj4-glibc-2.25-dev/include/features.h
./r2q001drj14szknyhvpq923f0v1m4sqa-wxwidgets-3.0.4/include/wx-3.0/wx/features.h
./f3l058q0zvnzr7nvl0jj789pyvljqadw-glibc-2.27-dev/include/features.h
./gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/include/c++/7.3.0/parallel/features.h

Additional info in my next message.

stephane-rolland commented 5 years ago

I have tried executing cling in a environment that would expose glibc-dev/include files. But I cannot seem to succeed there. my shell.nix file:

with import <nixpkgs> {}; {
  clingEnv = stdenv.mkDerivation {
    name = "clingeenv";
    buildInputs = [glibc];
  };
}

this only seem to put the glibc executables on the path, but NOT the headers: $ echo $PATH: nix/store/ps577kng0c652r6c4xks9jv5mksdxgyp-patchelf-0.9/bin:/nix/store/a2r3mx450ndsqiky685qp8d0ljsw0bx8-paxctl-0.9/bin:/nix/store/cy3x06bfplivhrvx6rf7vkszx81c09nn-gcc-wrapper-7.3.0/bin:/nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/bin:/nix/store/8bh94qdmga1zkb85li56380i44ay82cs-glibc-2.27-bin/bin:/nix/store/68z2cvbzws1pn0z8dhgfkmws75r2z7gm-coreutils-8.29/bin:/nix/store/5c5vbvcybxllw3jdwzm1s0gx7j1464rc-binutils-wrapper-2.30/bin:/nix/store/5vyv136pqs75pj0b8vcpdyc03dmn9p0n-binutils-2.30/bin:/nix/store/8bh94qdmga1zkb85li56380i44ay82cs-glibc-2.27-bin/bin:/nix/store/68z2cvbzws1pn0z8dhgfkmws75r2z7gm-coreutils-8.29/bin:/nix/store/8bh94qdmga1zkb85li56380i44ay82cs-glibc-2.27-bin/bin:/nix/store/68z2cvbzws1pn0z8dhgfkmws75r2z7gm-coreutils-8.29/bin:/nix/store/6ddj3i7yqdl8d6gk09c1sj4nqhb0ny8p-findutils-4.6.0/bin:/nix/store/ih08f196x70ypll72rihakqslf0j44kf-diffutils-3.6/bin:/nix/store/j2kj1w5glbr5pg39ssihqk5622jjsghs-gnused-4.5/bin:/nix/store/xkzmszz7vp1wdgbpyfvb1wns2qlx9mhz-gnugrep-3.1/bin:/nix/store/s2lj670i2vf2wbq2dnl32c2wb6xf5li1-gawk-4.2.1/bin:/nix/store/n9w6xkk15nkpslvzhwrpi90pv3kkdal6-gnutar-1.30/bin:/nix/store/p1n5m7xp9b3pxs30ry5anzq4ql7zxmly-gzip-1.9/bin:/nix/store/3kzrxhyp633qm4w532jd2qjv8rfvgjhx-bzip2-1.0.6.0.1-bin/bin:/nix/store/8m2ld502dsx6rbsvv05597qzxha4cnc1-gnumake-4.2.1/bin:/nix/store/b9p787yqaqi313l9rr0491igjwyzqfmw-bash-4.4-p23/bin:/nix/store/c8crwa3807d4blaqb4sbqksbyxqqigh2-patch-2.7.6/bin:/nix/store/n8v50b5qczjvsa5hgl41iccqk51xh2r0-xz-5.2.4-bin/bin:/home/code/bin:/run/wrappers/bin:/home/code/.nix-profile/bin:/nix/var/nix/profiles/default/bin:/run/current-system/sw/bin:/etc/profiles/per-user/code/bin

Although the glibc headers are clearly in my nix-store, I still have not find a way to expose them with a shell.nix and a buildInputs declaration.

stephane-rolland commented 5 years ago

Further more, on IRC, @symphorien has advised me to look at what flags are added by the compiler wrappers. So with

$ nix-shell -p clang 
$ export NIX_DEBUG=1

this flag is indeed added properly:

  -idirafter
  /nix/store/f3l058q0zvnzr7nvl0jj789pyvljqadw-glibc-2.27-dev/include

But if I launch $ ./result/bin/clang, there are no flags (absolutely none) that are added.

@symphorien also advised me to check about the compiler wrappers, which are responsible for automatically adding flags to compiler calls in nixos.

But I have not managed to understand how/where to use wrapCC so as to wrap this custom clang compiler that has been built by the cling build.

That is really likely to be related to the issue. So I would like to cc-wrap this custom clang used by cling.

I found one example which I think uses this mechanism, but I have not figured it out how to reuse this in my case: https://discourse.nixos.org/t/approaches-for-building-packages-with-proprietary-compilers-and-libraries-with-nix/768/10

I'm gonna to read more about cc-wrapper. But if you have an example nix file doing this, it would be welcome. I'm gonna try checking in nixpkgs if I can get something.

symphorien commented 5 years ago

See https://github.com/NixOS/nixpkgs/pull/40746 for an example of wrapping a compiler.

veprbl commented 5 years ago

Regarding glibc issue, you might need to set a similar option to what is used in ROOT: https://github.com/NixOS/nixpkgs/blob/2c074fc6c8d278a8e8e7c3bfec42b7e762199fb4/pkgs/applications/science/misc/root/default.nix#L63

From my experience with ROOT and nixpkgs I can say that you probably do not want to use the cc wrapper.

stephane-rolland commented 5 years ago

@veprbl I have build cling with this cmake flag. I have taken all the other flags also indeed. Builds nicely, but still the same issue. when running cling still doesnt see glibc headers.

I'm gonna check with a cc-wrapper.

In nixpkgs there is this example for webassembly emscripten compiler being wrapped for nixos. It seems to be close to what I want to achieve in the case of cling using a modified clang:

{ newScope, stdenv, binutils, wrapCCWith, symlinkJoin }:
let
  callPackage = newScope (self // {inherit stdenv;});

  self = {
    emscriptenfastcomp-unwrapped = callPackage ./emscripten-fastcomp.nix {};
    emscriptenfastcomp-wrapped = wrapCCWith {
      cc = self.emscriptenfastcomp-unwrapped;
      # Never want Apple's cctools for WASM target
      bintools = binutils;
      libc = stdenv.cc.libc;
      extraBuildCommands = ''
        # hardening flags break WASM support
        cat > $out/nix-support/add-hardening.sh
      '';
    };
    emscriptenfastcomp = symlinkJoin {
      name = "emscriptenfastcomp-${stdenv.lib.getVersion self.emscriptenfastcomp-unwrapped}";
      paths = [ self.emscriptenfastcomp-wrapped self.emscriptenfastcomp-unwrapped ];
      preferLocalBuild = false;
      allowSubstitutes = true;
      postBuild = ''
        # replace unwrapped clang-3.9 binary by wrapper
        ln -sf $out/bin/clang $out/bin/clang-[0-9]*
      '';
    };
  };
in self
veprbl commented 5 years ago

@stephane-rolland You might want to check if cling ever executes clang. My understanding that it does not (ROOT itself might use system's compiler in ACLiC, but that's unrelated).

stephane-rolland commented 5 years ago

@veprbl you are totally right. When provoking a segfault feeding cling with #include <iostream>;, the stacktrace displays function calls to a clang library, not calling the clang process.

$ ar -t ..../lib/libclangParse.a exposes Parser.cpp.o which extremely likely defines the clang::Parser::ParseTopLevelDecl function seen in the stacktrace.

So I now tend to think like you that wrapping the compiler will not help.

veprbl commented 5 years ago

@stephane-rolland I think you should try digging into this "C_INCLUDE_DIRS" setting.

stephane-rolland commented 5 years ago

@veprbl yep. Anyway, I have also checked artifically adding the glibc dev include to the path: $ export PATH=$PATH:/nix/store/f3l...../glibc-...-dev/include and cling does not behave any better.

Your suggestion seems the most promising. But the feedback loop for trying is not short, it takes more than one hour to compile on my machine :-)

stephane-rolland commented 5 years ago

While looking around I have re-read the warning messages at the launching of cling and indeed they are related to gcc header files trying to include this file. @veprbl with your experience of ROOT, don't you think it is strange that cling may rely on some gcc header files? It may be unrelated, but I'm wondering.

In file included from /nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/lib/gcc/x86_64-unknown-linux-gnu/7.3.0/../../../../include/c++/7.3.0/new:39:
In file included from /nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/lib/gcc/x86_64-unknown-linux-gnu/7.3.0/../../../../include/c++/7.3.0/x86_64-unknown-linux-gnu/bits/c++config.h:533:
/nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/lib/gcc/x86_64-unknown-linux-gnu/7.3.0/../../../../include/c++/7.3.0/x86_64-unknown-linux-gnu/bits/os_defines.h:39:10: fatal error: 'features.h' file not found
#include <features.h>
veprbl commented 5 years ago

But the feedback loop for trying is not short, it takes more than one hour to compile on my machine :-)

For starters you just need to make it build outside of nix. Also could try using ccache to speed things up.

@veprbl with your experience of ROOT, don't you think it is strange that cling may rely on some gcc header files?

cling may not need those, but libc and/or the C++ standard library can include them.

There is always a possibility that the crash is unrelated to missing header files. cling is not supposed to crash because of those.

stephane-rolland commented 5 years ago

Three interesting stuffs: I reproduce the error/warning (without a crash on segfault) in cling doing simply:

[cling]$ #include <cstdio>
In file included from input_line_3:1:
In file included from /nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/include/c++/7.3.0/cstdio:41:
In file included from /nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/include/c++/7.3.0/x86_64-unknown-linux-gnu/bits/c++config.h:533:
/nix/store/gfbrmbcswqnm7r8y9jx5v6wf2zjyzhhk-gcc-7.3.0/include/c++/7.3.0/x86_64-unknown-linux-gnu/bits/os_defines.h:39:10: fatal error: 'features.h' file not found
#include <features.h>
         ^~~~~~~~~~~~

Searching about the two error messages below made me find on git-hub this opened issue: https://github.com/tweag/jupyterWith/issues/24 opened by @MMesch

I think it is totally related.

$ ./result/bin/cling -print-libgcc-file-name
libgcc.a
No Command jobs were built.
Could not get cc1 arguments.
Compiler instance could not be created.
Could not create Interpreter instance: No such file or directory
$ ./result/bin/cling -print-search-dirs
programs: =./result/bin:/..//bin
libraries: =/nix/store/m8rhb53x4n97x73wg3kks0i01i1c570s-cling/bin/../lib/clang/5.0.0:./result/bin/../lib
No Command jobs were built.
Could not get cc1 arguments.
Compiler instance could not be created.
Could not create Interpreter instance: Illegal seek
stephane-rolland commented 5 years ago

Besides, listing all the flags (there are tons of them) available for cling, I namely have these:

I'm gonna check if using them can help temporarily.

veprbl commented 5 years ago

Looking at https://github.com/conda-forge/cling-feedstock/issues/18 there is some useful information. It also shows that this bug is not relevant to nix.

stephane-rolland commented 5 years ago

@veprbl and they have fixed it: I have used/played with this conda-forge cling package at the beginning of this week.

stephane-rolland commented 5 years ago

Without success, I have tried this added to my build.nix file inpsired by the root nix package:

the main modification is the ++ stdenv.lib.optional (stdenv.cc.libc != null) "-DCLING_INCLUDE_PATH=${stdenv.lib.getDev stdenv.cc.libc}/include" based on the solution achieved in https://github.com/conda-forge/cling-feedstock/issues/18

cmakeFlags = [
        "-Drpath=ON"
        "-DCMAKE_INSTALL_LIBDIR=lib"
        "-DCMAKE_INSTALL_INCLUDEDIR=include"
        "-Dalien=OFF"
        "-Dbonjour=OFF"
        "-Dcastor=OFF"
        "-Dchirp=OFF"
        "-Ddavix=OFF"
        "-Ddcache=OFF"
        "-Dfftw3=OFF"
        "-Dfitsio=OFF"
        "-Dfortran=OFF"
        "-Dimt=OFF"
        "-Dgfal=OFF"
        "-Dgviz=OFF"
        "-Dhdfs=OFF"
        "-Dkrb5=OFF"
        "-Dldap=OFF"
        "-Dmonalisa=OFF"
        "-Dmysql=OFF"
        "-Dodbc=OFF"
        "-Dopengl=ON"
        "-Doracle=OFF"
        "-Dpgsql=OFF"
        "-Dpythia6=OFF"
        "-Dpythia8=OFF"
        "-Drfio=OFF"
        "-Dsqlite=OFF"
        "-Dssl=OFF"
        "-Dxml=ON"
        "-Dxrootd=OFF"
      ]
      ++ stdenv.lib.optional (stdenv.cc.libc != null) "-DC_INCLUDE_DIRS=${stdenv.lib.getDev stdenv.cc.libc}/include"
      ++ stdenv.lib.optional (stdenv.cc.libc != null) "-DCLING_INCLUDE_PATH=${stdenv.lib.getDev stdenv.cc.libc}/include"
      ++ stdenv.lib.optional stdenv.isDarwin "-DOPENGL_INCLUDE_DIR=${OpenGL}/Library/Frameworks";

    enableParallelBuilding = true;
    buildPhase = ''
      mv clang llvm/tools
      mv cling llvm/tools
      mkdir -p $out
      mkdir build
      cd build
      cmake -DCMAKE_INSTALL_PREFIX=$out -DLLVM_ENABLE_FFI=ON -DLLVM_ENABLE_RTTI=ON -DLLVM_INSTALL_UTILS=ON -DCMAKE_BUILD_TYPE=Release ../llvm
      cmake --build .
      cmake --build . --target install
    '';

Much probably much of my added flags are not relevant. I just copy.pasted from the root nix package. But my main concern is that defining cmakeFlags in nix langauge, and later invoking cmake with defined flags in the buildPhase: cmake -DCMAKE_INSTALL_PREFIX=$out -DLLVM_ENABLE_FFI=ON -DLLVM_ENABLE_RTTI=ON -DLLVM_INSTALL_UTILS=ON -DCMAKE_BUILD_TYPE=Release ../llvm could be interfering.

thomasjm commented 5 years ago

Hey, just noticed this discussion -- since I posted the original version I had issues with include files also and made some changes. If you look at the latest version on my fork I added an -isystem flag, see here: https://github.com/codedownio/nixpkgs/blob/codedown-19.06/pkgs/applications/science/misc/root/cling.nix . Hopefully that helps.

stephane-rolland commented 5 years ago

@thomasjm It helps!

Notice: I have had to add the line nativeBuildInputs = [ pkgs.makeWrapper] to your file otherwise the call to wrapProgram was failing because unrecognized during the install phase.

cling behaves a little better: it starts without error messages.

However it still emits errors or crashes on segfault for code like #include <functional> or

#include <iostream>
void test () { std::cout << "hello" << std::endl; };

Also I wanted to check what/whetherwrapProgram was adding flags at runtime: but $ export NIX_DEBUG=1 or higher then invoking cling does not show any flag that would be added by nix when launching cling.

thomasjm commented 5 years ago

Oh right, I don't know why makeWrapper isn't there--I would put it in the regular buildInputs rather than nativeBuildInputs though.

The code you mention is importing C++ headers. We probably need to add an -isystem flag for those too since we only added C headers so far. I don't know off the top of my head what Nix package would provide those. FYI if you want to try to figure it out, you can quickly experiment by doing

nix-build [build the cling you currently have] -o ./cling
./cling -isystem /new/path/that/might/have/the/cpp/headers/
# note that this should invoke cling with the new -isystem you add *plus* the one makeWrapper added

Also FYI in response to your last question -- makeWrapper replaces the existing executable with a short shell script that calls it, so you can just cat the wrapped output and you should see the flags.

stephane-rolland commented 5 years ago

@thomasjm Related to your latest proposal: Indeed the c++ headers are already found, but it's stdlib.h that cannot be found when including <functional> header. However I have to try wrapProgram with something about libstdcxx5.

Not related to your last proposal: In your file you have commented propagatedBuildInputs out. When re-using it, it makes the build stop on error because of stdlib no longer reachable. I feel really ill at ease with this behaviour. Again it's stdlib that cannot be seen anylonger.

It seems you have used the wrapProgram option so as to circumvent this issue.

Do you have any idea what could provoke this ? Using glibc glibc.dev in propagateBuildInputs seems to make stdlib.h no longer seen by c++ headers during cling building.

As there is a similarity between the two points, I try to understand that more clearly. Personnally I have no idea about that for the moment. At best, maybe it could be related to the version of nixos.glibc. Just a an assumption.

Furthermore, I have tried using nixos.clang++ instead of gcc for building the whole thing. And then again there are some not so obvious conflicts in using llvmPackages_x.libcxx and llvmPackages_x.libcxxabi together with glibc while building cling. The cstdlib from libcxx is then no longer able to access the sheer C definitions of some functions, namely those encapsulated by std in <cmath>, for example. Which makes me assume about another conflict when using nixos.glibc. In my case I still use the 18.09 channel, with glibc 2-27 IIRC. I don't know which version of glibc is on unstable channel.

thomasjm commented 5 years ago

Do you have any idea what could provoke this ?

My general impression back when I was working on this is that the C/C++ compiler machinery looks in various places for include files, so if you have multiple options then one of them will take precedence, and if the one that takes precedence is messed up somehow it could break the build. FWIW the Nixpkgs manual describes the CC Wrapper setup hook as "convoluted" :P

I'm hoping that building cling with different options like you describe isn't necessary, since it's so time-consuming. I think my strategy (when I find time to work on this) will be to start with the version I successfully built, and experiment with launching it with different options until it can import/call C and C++ functions successfully. I think studying https://github.com/conda-forge/clangdev-feedstock/pull/45 and https://github.com/conda-forge/clangdev-feedstock/pull/46 might be helpful also.

thomasjm commented 5 years ago

Oh @stephane-rolland I think I figured it out and it's a one-word fix :). Just change -isystem to -idirafter. The former was screwing up the import search path by putting the glibc include path ahead of the standard system search paths; see here.

See my latest branch for the current version. I'll open a PR for this once I confirm everything looks good.

stephane-rolland commented 5 years ago

You rock! I have tested it, and it looks fine. Many thanks, I was looking forward to using cling on Nixos!

stephane-rolland commented 4 years ago

I confirm it was ok back then in July 2019 when I was testing it, but I was using NixOS 19.03.

Since I use 19.09 however, I did three or four checks , and I got errors building cling at 3/4 different places. But the errors seems different than before: they don't happen at compile stage, but at linking stage.

Each time (for example it was at 94%,95%, and 72% progress during build) there was no sufficient information in the error message. Something like "make failed with exit code 2", which means "Make Encountered Errors".

I have not investigated further yet.

stale[bot] commented 4 years ago

Hello, I'm a bot and I thank you in the name of the community for opening this issue.

To help our human contributors focus on the most-relevant reports, I check up on old issues to see if they're still relevant. This issue has had no activity for 180 days, and so I marked it as stale, but you can rest assured it will never be closed by a non-human.

The community would appreciate your effort in checking if the issue is still valid. If it isn't, please close it.

If the issue persists, and you'd like to remove the stale label, you simply need to leave a comment. Your comment can be as simple as "still important to me". If you'd like it to get more attention, you can ask for help by searching for maintainers and people that previously touched related code and @ mention them in a comment. You can use Git blame or GitHub's web interface on the relevant files to find them.

Lastly, you can always ask for help at our Discourse Forum or at #nixos' IRC channel.

stephane-rolland commented 4 years ago

I have updated @thomasjm nix file with the latest head revision & sha256 for cling, cland, and llvm. The compilation of LLVM still seems to have an issue.

I have tried with different revisions of LLVM, (with one month of commit history less each time), and they all break.

EDIT: this paragraph below is a totally wrong track, I had not seen the error in the build log which appears long before the build breaks.

I have found an extremely similar issue (not related to nixos) from March 2017, with the build of LLVM but for MacOS. In that thread, they say thing should go smooth if disabling compiler-rt. They were suggesting an issue with the build system of the person who opened the ticket.

According to this thread, it should be possible to circumvent the error by removing the compilation flag -DLLVM_ENABLE_ASSERTIONS=ON from the build of LLVM.

For the moment I don't know how to make nix-build+CMake much more verbose, as the real error is almost NOT displayed at all. It only outputs: make: *** [Makefile:152: all] Error 2 . => I'd like to check if the error is indeed the same as (https://github.com/llvm-hs/homebrew-llvm/issues/3), i.e. https://gist.github.com/zmactep/6376b7d025eacc1d8c33c6283bbb30d5#file-gistfile1-txt-L938.

veprbl commented 4 years ago

@stephane-rolland It would help for people to understand the issue if you provided your build logs and/or expressions. CMake doesn't hide the error messages, but you might appear in the middle of the log if you build with many cores (enableParallelBuilding = true;). If you want a more verbose output, you could set VERBOSE=1;.

stephane-rolland commented 4 years ago

@veprbl Thanks, you're right: the error message appears much before the building ends on error.

The first error appears ca. 440 lines before the build eventually ends: logs here There are two types of recurring errors, both seems related to std::vector<llvm::StringRef>

The most frequent is: error: no matching function for call to 'std::vector<llvm::StringRef>::vector(std::vector<std::__cxx11::basic_string<char> >)' uniques(uniqueEnumsInOrder(enums))

This one appears repeatedly close to the end of the build: error: conversion from 'vector<std::__cxx11::basic_string<char>>' to non-scalar type 'vector<llvm::StringRef>' requested

On stackoverflow someone seem to have had a similar issue: https://stackoverflow.com/questions/46893355/llvm-build-error-due-to-no-matching-function . He says he had to switch from gcc 7.2.0 back to gcc 5.4.0 for compilation to succeed. That does not seem a viable solution.

this is the nix expression used for nix-build:

with import <nixpkgs> {}; {

clingEnv = stdenv.mkDerivation rec {
  name = "cling";

 clingSrc = fetchFromGitHub {
    owner = "root-project";
    repo = "cling";
    rev = "4b5ad54a0ab4a9d669cc416825832f96901d1774";
    sha256 = "0dw1xf586iya5a1pd6vxl4larl2y8a9qxxv9h11qhlawp49csfwx";
  };

  clangSrc = fetchgit {
    url = "http://root.cern.ch/git/clang.git";
    rev = "58199aaa59e063e6386d5672178af1bfce184f2b"; # This is the head of the cling-patches branch
    sha256 = "1qjhi7sjh0wv9p0z30k6xd7jchfl2312cy5fshm070vx6rvf4wqx";
  };

  llvmSrc = fetchgit {
    url = "http://root.cern.ch/git/llvm.git";
    rev = "3c8af5480a208e84dc6ffc24285611c15b51177b"; # head
    sha256 = "0xnc6v53d7ddn0k2zfxhjy93fpfhlq37glxdck5ds7li212rgir0";
   };

  unpackPhase = ''
    runHook preUnpack

    cp -r "$llvmSrc/." .
    chmod u+w ./tools
    mkdir -p ./tools/cling && cp -r "$clingSrc/." ./tools/cling
    mkdir -p ./tools/clang && cp -r "$clangSrc/." ./tools/clang

    chmod -R u+w .

    runHook postUnpack
  '';

  nativeBuildInputs = [ cmake makeWrapper python ];
  buildInputs = [ libffi ];

  cmakeFlags = [
    "-DLLVM_ENABLE_FFI=ON"
    "-DLLVM_ENABLE_RTTI=ON"
    "-DLLVM_INSTALL_UTILS=ON"
    "-DLLVM_ENABLE_ASSERTIONS=ON"
  ];

  postInstall = ''
    wrapProgram $out/bin/cling --add-flags "-idirafter ${glibc.dev}/include"
  '';
};
}
veprbl commented 4 years ago

Why not just revert 0fc62807153bd91bc8245aa103010f05a26546fc and use llvm_4?

stephane-rolland commented 4 years ago

When I check the cmake configuration of the llvm sources git repository, there's this line:

CMAKE_CXX_COMPILER /nix/store/291ldi6fqsbmkbvbs8is4mcg3jb64ld4-gcc-wrapper-8.3.0/bin/g++

Thus, I cannot see clearly how reverting commit "0fc66280..." would have effect on the building of this custom llvm version. (Notice that it does not come from: https://github.com/llvm - It comes from: http://root.cern.ch/git/llvm.git)

However I like your idea of changing compiler. Going to try that.

stephane-rolland commented 4 years ago

I have tried different gcc versions, and different clang version to compile this llvm... no success, always the same kind of error messages.

@veprbl I found a message pointing in a direction similar as you suggest: https://lists.llvm.org/pipermail/llvm-dev/2017-July/115213.html , claiming that the Clang and Llvm versions may be incompatible.

Maybe I should ask directly the guys from the original Root and Cling project.

stephane-rolland commented 4 years ago

A little step that makes llvm compiles ok:

When I remove the two steps in the unpackPhase taking care of the tools directory of root.clang and root.cling:

unpackPhase = ''
    runHook preUnpack
    cp -r "$llvmSrc/." .
    chmod u+w ./tools
    # mkdir -p ./tools/cling && cp -r "$clingSrc/." ./tools/cling
    # mkdir -p ./tools/clang && cp -r "$clangSrc/." ./tools/clang
    chmod -R u+w .
    runHook postUnpack
    '';

then root.llvm compiles nicely without the error messages complaining about std::vector<llvm::StringRef>, using nixos compiler nixpkgs.clang_9.

I will re-add the steps one by one to see when the issue start to happen. And check different compilers also.

stephane-rolland commented 4 years ago

I was much probably on a wrong track. Looking at the source code of the Cling Packaging Tool which is normally used for other Linuxes: https://github.com/root-project/cling/tree/master/tools/packaging , they do not seem to use the latest HEAD rev as I was naively trying to do.

Instead they use a special version: what is returned by an HttpRequest at https://raw.githubusercontent.com/root-project/cling/master/LastKnownGoodLLVMSVNRevision.txt - with the explicit name "Last Known Good LLVM Svn Revision"

It currently returns over the web: "release_50" , which most probably does not correspond to git HEAD revision of root-llvm.

As seen from the code of Cling Packaging Tool in the file cpt.py, I also probably have to mimic different steps seen here: https://github.com/root-project/cling/blob/master/tools/packaging/cpt.py#L188

Namely there are mention of Cling patches applied to llvm.

Gonna have a closer look at that.

stephane-rolland commented 4 years ago

Got stuck from the start: I have asked the question about the url which gives me a 404 error for retrieveing cling patches: https://github.com/root-project/cling/issues/356