cpmech / russell

Rust Scientific Libary. ODE and DAE (Runge-Kutta) solvers. Special functions (Bessel, Elliptic, Beta, Gamma, Erf). Linear algebra. Sparse solvers (MUMPS, UMFPACK). Probability distributions. Tensor calculus.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

russell_lab blas build

m4b opened this issue · comments

commented

Hello, nice library!

On my archlinux system, I have openblas installed, and it's headers are at /usr/include/openblas/cblas.h; for whatever reason, when building I get this error:

  running: "cc" "-O0" "-ffunction-sections" "-fdata-sections" "-fPIC" "-gdwarf-4" "-fno-omit-frame-pointer" "-m64" "-Wall" "-Wextra" "-o" "/home/m4b/git/russell/target/debug/build/russell_lab-8efc726f530eb1fc/out/c_code/interface_blas.o" "-c" "c_code/interface_blas.c"
  cargo:warning=c_code/interface_blas.c:18:10: fatal error: cblas.h: No such file or directory

  cargo:warning=   18 | #include "cblas.h"

  cargo:warning=      |          ^~~~~~~~~

  cargo:warning=compilation terminated.

  exit status: 1

  --- stderr

In attempting to debug, I discovered I can pass:

RUSSELL_LAB_USE_INTEL_MKL=1

However, more rustish would (probably) be to use a feature flag to opt into using the intel api.

Regardless I think finding the headers should succeed, it looks like this else branch in the build.rs needs slightly better handling:

        // OpenBLAS
        cc::Build::new()
            .file("c_code/interface_blas.c")
            .compile("c_code_interface_blas");
        println!("cargo:rustc-link-lib=dylib=openblas");
        println!("cargo:rustc-link-lib=dylib=lapack");

There is also pkgconf which people usually use for this purpose to find headers, etc., e.g.:

pkgconf --cflags-only-I cblas
-I/usr/include/openblas

returns the correct path (and there is a rust crate to use at build time for this).

Lastly, and this is only partially related, the only function I'm using here is: https://docs.rs/russell_lab/0.7.2/russell_lab/matrix/fn.mat_pseudo_inverse.html

which works perfectly for me (thank you, it's results are identical in my test cases to the matlab and octave pinv), and it would be more ideal if this were pure rust and I could opt out of the blas linkage, but that is probably infeasible, and anyway, another issue entirely :)

Anyway, thanks for the great library!

Hi, thank you for your suggestions! I've implemented most of them in the crate version 0.8.0 (pull request: #76)

First, Concerning cblas.h on Arch Linux, I've added a search to /usr/include/openblas in build.rs (see 15777b9). Hence, all should work now even without Intel MKL.

Second, it is a great idea to use Rust's features approach! So, I've implemented two optional features:

  • (default) no feature specification required. The code works with default dependencies
  • local_libs will require the sparse solvers compiled in /usr/local/...
  • intel_mkl (will enable local_libs too) will require the installation of Intel tools

For instance, to use Intel MKL:

cargo build --features intel_mkl

Third, I've tried to use pkg-config here, but will need more time to properly use it. I also want to see if more libraries are needed. So, this goes to my TODO list for now 😊

Good to hear that the pseudo inverse matches Octave's pinv (and Matlab). They use the same code base, effectively (OpenBLAS or Intel MKL). It would be hard to replace these ancient libraries...

Cheers.

commented

Nice that was fast!

I tested latest git, and can confirm, this now works without env variables on my system, out of the box, and building with --features intel_mkl works as well, great stuff!

On that note, w.r.t. features the only general recommendation I've heard is that they are "additive" (i.e., two separate crates both dependent on a library with two features, one turning on one feature, and another crate turning on a separate feature, does not cause breakage in the downstream crate that might include both, as it has an "action at a distance feel", e.g., they change the signature of a function, depending on which is set, etc.); given how you've implemented it, this seems to satisfy this condition, though it can be tricky/not feasible when it comes to different build flags, using different native libraries, etc.

Thanks for working on this library :) will close this issue as confirmed it is fixed