Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ld error while building Mercurial with Rust #71

Open
paugier opened this issue Dec 8, 2020 · 13 comments
Open

ld error while building Mercurial with Rust #71

paugier opened this issue Dec 8, 2020 · 13 comments

Comments

@paugier
Copy link

paugier commented Dec 8, 2020

I tried to build Mercurial with Rust from conda-forge. I did

conda create -n env_hg_rust setuptools rust -y
conda activate env_hg_rust
wget https://www.mercurial-scm.org/release/mercurial-5.6.1.tar.gz
tar -xvf mercurial-5.6.1.tar.gz
cd mercurial-5.6
python setup.py --rust install

It ends with an error related to the fact that the linker can't find libz:

note: /data0/opt/miniconda3/envs/env_hg_rust/bin/../lib/gcc/x86_64-conda-linux-gnu/9.3.0/../../../../x86_64-conda-linux-gnu/bin/ld: cannot find -lz

I find it strange that /data0/opt/miniconda3/envs/env_hg_rust/x86_64-conda-linux-gnu/bin/ld can't find /data0/opt/miniconda3/envs/env_hg_rust/lib/libz.so.

I tried simple things with LIBRARY_PATH and LD_LIBRARY_PATH but without success.

I don't know if it is something related with Rust or just a conda bug. Do you see how to solve this problem?


Environment (conda list):
$ conda list
# packages in environment at /data0/opt/miniconda3/envs/env_hg_rust:
#
# Name                    Version                   Build  Channel
_libgcc_mutex             0.1                 conda_forge    conda-forge
_openmp_mutex             4.5                       1_gnu    conda-forge
binutils_impl_linux-64    2.35.1               h17ad2fc_0    conda-forge
ca-certificates           2020.11.8            ha878542_0    conda-forge
certifi                   2020.11.8        py39hf3d152e_0    conda-forge
gcc_impl_linux-64         9.3.0               h28f5a38_17    conda-forge
kernel-headers_linux-64   2.6.32              h77966d4_13    conda-forge
ld_impl_linux-64          2.35.1               hed1e6ac_0    conda-forge
libffi                    3.3                  h58526e2_1    conda-forge
libgcc-devel_linux-64     9.3.0               hfd08b2a_17    conda-forge
libgcc-ng                 9.3.0               h5dbcf3e_17    conda-forge
libgomp                   9.3.0               h5dbcf3e_17    conda-forge
libstdcxx-ng              9.3.0               h2ae2ef3_17    conda-forge
ncurses                   6.2                  h58526e2_4    conda-forge
openssl                   1.1.1h               h516909a_0    conda-forge
pip                       20.3               pyhd8ed1ab_0    conda-forge
python                    3.9.0           hffdb5ce_5_cpython    conda-forge
python_abi                3.9                      1_cp39    conda-forge
readline                  8.0                  he28a2e2_2    conda-forge
rust                      1.48.0               h36c2ea0_0    conda-forge
rust-std-x86_64-unknown-linux-gnu 1.48.0               hc1431ca_0    conda-forge
setuptools                49.6.0           py39h079e4ff_2    conda-forge
sqlite                    3.34.0               h74cdb3f_0    conda-forge
sysroot_linux-64          2.12                h77966d4_13    conda-forge
tk                        8.6.10               hed695b0_1    conda-forge
tzdata                    2020d                h516909a_0    conda-forge
wheel                     0.36.0             pyhd3deb0d_0    conda-forge
xz                        5.2.5                h516909a_1    conda-forge
zlib                      1.2.11            h516909a_1010    conda-forge

Details about conda and system ( conda info ):
$ conda info
     active environment : env_hg_rust
    active env location : /data0/opt/miniconda3/envs/env_hg_rust
            shell level : 1
       user config file : /home/pierre/.condarc
 populated config files : /home/pierre/.condarc
          conda version : 4.9.2
    conda-build version : not installed
         python version : 3.7.4.final.0
       virtual packages : __glibc=2.31=0
                          __unix=0=0
                          __archspec=1=x86_64
       base environment : /data0/opt/miniconda3  (writable)
           channel URLs : https://conda.anaconda.org/conda-forge/linux-64
                          https://conda.anaconda.org/conda-forge/noarch
                          https://repo.anaconda.com/pkgs/main/linux-64
                          https://repo.anaconda.com/pkgs/main/noarch
                          https://repo.anaconda.com/pkgs/r/linux-64
                          https://repo.anaconda.com/pkgs/r/noarch
          package cache : /data0/opt/miniconda3/pkgs
                          /home/pierre/.conda/pkgs
       envs directories : /data0/opt/miniconda3/envs
                          /home/pierre/.conda/envs
               platform : linux-64
             user-agent : conda/4.9.2 requests/2.24.0 CPython/3.7.4 Linux/5.4.0-56-generic ubuntu/20.04.1 glibc/2.31
                UID:GID : 1000:1000
             netrc file : /home/pierre/.netrc
           offline mode : False
@pkgw
Copy link
Contributor

pkgw commented Dec 9, 2020

Hmm, I'm not sure what's going on here. But I think that it's very unlikely that your problem is related to how conda-forge packages the Rust toolchain. The error is occurring at the level of conda-forge's C/binutils toolchain, but that toolchain is extremely well tested for basic operations like this. So, my best guess is that the Mercurial+Rust build system is somehow doing something unusual that triggers this error.

I'm going to close this because I just can't see that this issue would be related to how we're packaging Rust. I think you might have to dig deeper into how the Mercurial+Rust build is working.

@pkgw pkgw closed this as completed Dec 9, 2020
@isuruf
Copy link
Member

isuruf commented Dec 9, 2020

Try installing compilers package

@paugier
Copy link
Author

paugier commented Dec 9, 2020

Installing compilers does not help.

However, I think I understood and that this issue should be reopened and fixed so that cargo installed with conda really works 🙂

The problem is related to the fact that "cargo install does not respect LDFLAGS" rust-lang/cargo#3694 and that in conda, the library path miniconda3/envs/env_hg_rust/lib is only given in this environment variable.

$LDFLAGS                                                                                                                                                      
'-Wl,-O2 -Wl,--sort-common -Wl,--as-needed -Wl,-z,relro -Wl,-z,now -Wl,--disable-new-dtags -Wl,--gc-sections -Wl,-rpath,/data0/opt/miniconda3/envs/env_hg_rust/lib -Wl,-rpath-link,/data0/opt/miniconda3/envs/env_hg_rust/lib -L/data0/opt/miniconda3/envs/env_hg_rust/lib'

Therefore cargo cannot find libraries in miniconda3/envs/env_hg_rust/lib.

I was able to compile Mercurial by setting RUSTFLAGS to -L/data0/opt/miniconda3/envs/env_hg_rust/lib.

https://doc.rust-lang.org/cargo/reference/environment-variables.html#environment-variables-cargo-reads

Adding the other options that are in LDFLAGS in RUSTFLAGS does not work.

@pkgw pkgw reopened this Dec 9, 2020
@pkgw
Copy link
Contributor

pkgw commented Dec 9, 2020

Thanks for digging a bit deeper, that helps clarify the discussion.

I'm not sure how we should approach this. I kind of want to say that this sort of default search path stuff is the job of the lower-level toolchain, and if there's any problem here it should be addressed at that level rather than in Rust. But I don't understand the semantics of the default library search paths in the compilers that we ship, and I could see that maybe a default RUSTFLAGS environment setting would be appropriate.

@paugier
Copy link
Author

paugier commented Dec 9, 2020

I don't understand why rustc doesn't take into account LDFLAGS. I mean it uses the linker (via x86_64-conda-linux-gnu-cc) so it should pass the values in LDFLAGS to x86_64-conda-linux-gnu-cc.

I think for conda, the options -Wl,-rpath,/data0/opt/miniconda3/envs/env_hg_rust/lib -Wl,-rpath-link,/data0/opt/miniconda3/envs/env_hg_rust/lib are important. It seems that it is impossible to use them with cargo.

@pkgw
Copy link
Contributor

pkgw commented Dec 9, 2020

My guess is that the aim is to encourage reproducibility and explicitness in build processes. We may be accustomed to injecting low-level linker flags from environment variables, but it's really not a great method because it adds invisible statefulness to the build.

But anyway, even if we were all convinced that rustc should obey LDFLAGS, we shouldn't make such a change in our Rust package, I think — that would be a pretty profound behavior change to apply in a vendor patch. For this feedstock, I think the question is whether we should be setting up a default RUSTFLAGS environment variable or something.

@isuruf
Copy link
Member

isuruf commented Dec 9, 2020

@paugier, can you try installing rust_linux-64?

@paugier
Copy link
Author

paugier commented Dec 9, 2020

I tried with rust_linux-64 => same problem...

@paugier
Copy link
Author

paugier commented Dec 10, 2020

Note that it works with RUSTFLAGS set to

-C link-arg=-Wl,-rpath-link,/data0/opt/miniconda3/envs/env_hg_rust/lib -C link-arg=-Wl,-rpath,/data0/opt/miniconda3/envs/env_hg_rust/lib -L/data0/opt/miniconda3/envs/env_hg_rust/lib

But it does not seem to work with CARGO_BUILD_RUSTFLAGS (as defined in https://github.com/conda-forge/rust-activation-feedstock/blob/master/recipe/activate.sh).

@jinlow
Copy link

jinlow commented May 5, 2022

I'm having this same issue with rust 1.60 installed from conda-forge, on Ubuntu 21.10.

note: /home/jinlow/miniconda3/envs/rust_dev/bin/../lib/gcc/x86_64-conda-linux-gnu/7.5.0/../../../../x86_64-conda-linux-gnu/bin/ld: cannot find -lz
          collect2: error: ld returned 1 exit status

@jinlow
Copy link

jinlow commented May 5, 2022

However, @paugier's fix worked for me, running the following before building.

export RUSTFLAGS="-C link-arg=-Wl,-rpath-link,$CONDA_PREFIX/lib -C link-arg=-Wl,-rpath,$CONDA_PREFIX/lib -L$CONDA_PREFIX/lib"

@andronat
Copy link

JFYI we recently had to build a wheel package that includes a Rust binary inside a conda environment and we stumbled on this problem. using the RUSTFLAGS from @jinlow made the trick 😄

@andronat
Copy link

I also noticed that https://github.com/conda-forge/rust-activation-feedstock/blob/main/recipe/activate.sh#L19 adds RUSTFLAGS in the env.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants