When I add proc-macro = true to Cargo.toml I am not able to use rust-analyser debug lens on any test in lib.rs anymore. I get:
error while loading shared libraries: libtest-95a0f3dcb2265cb8.so:
cannot open shared object file: No such file or directory
Related
This is my first attempt at rust, I am from a c++ background and trying to get going. So I started to create my project in a folder called .../rust/
Note: I used this link to get started with the tools: https://medium.com/#wizofe/cross-compiling-rust-for-arm-e-g-raspberry-pi-using-any-os-11711ebfc52b
I have created the default rust program using: cargo new --bin rust_test. This creates .../rust/rust_test.
I can build using: cargo build or cargo build --target=armv7-unknown-linux-gnueabihf (for my BeagleBB)
So far so good. Now I want to create a library that I can share with other projects. But I will create it inside the rust_test folder as .../rust/rust_test/utils:
Created the library with: cargo new --lib utils
I can build my utils in side the utils dir with: cargo build, this generates a .rlib file.
Now I wanted to get my rust_test project to build it as a dependency, I found I just had to add: utils = { path = "utils" } to my rust_test .toml file.
Now I can build my rust_test executable and my utils lib in the rust_test folder with cargo build
Again, all good so far. The final part of the puzzle for me is to use the function within my utils library. There are two functions in there. One called adder(a,b) - an attempt at a template function, and a basic function called test123(). This is where I have got stuck. I can't seem to formulate the correct syntax to call either of these functions.
Here are my main files:
rust_test
location: .../rust/rust_test/
Cargo.toml
[package]
name = "rust_test"
version = "0.1.0"
authors = ["test#gmail.com <test#gmail.com>"]
edition = "2018"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
utils = { path = "utils" }
main.rs
mod utils;
fn main() {
println!("Hello, world!");
utils::test123(); // ??? - does not work
}
utils
location: .../rust/rust_test/utils/
Cargo.toml
[package]
name = "utils"
version = "0.1.0"
authors = ["test#gmail.com <test#gmail.com>"]
edition = "2018"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
lib.rs
#[cfg(test)]
mod tests {
#[test]
fn adder<T>(a: T, b: T) -> T {
return a + b;
}
}
#[cfg(utils)]
mod utils {
#[utils]
fn test123() {
println!("test!");
}
}
The output
~/bbb/development/rust/rust_test$ cargo build
Compiling rust_test v0.1.0 (/home/user/bbb/development/rust_test)
error[E0583]: file not found for module `utils`
--> src/main.rs:1:1
|
1 | mod utils;
| ^^^^^^^^^^
|
= help: to create the module `utils`, create file "src/utils.rs"
error[E0425]: cannot find function `test123` in module `utils`
--> src/main.rs:6:12
|
6 | utils::test123(); // ??? - does not work
| ^^^^^^^ not found in `utils`
error: aborting due to 2 previous errors
Some errors have detailed explanations: E0425, E0583.
For more information about an error, try `rustc --explain E0425`.
error: could not compile `rust_test`.
I have to admit I don't really understand what the #[cfg...] and #[...] lines do. But from what I have read I thought the mod utils; in main.rs tells the rust compiler/linker to look else where for the test123() function.
Maybe I have not even linked the files at all yet - I have only built them?
So the question is what do I need to do now to link my library to my application so I can use the lib function test123()?
update
if I remove mod utils; I get the error:
user#user-VirtualBox:~/bbb/development/rust/rust_test$ cargo build
Compiling rust_test v0.1.0 (/home/user/bbb/development/rust_test)
error[E0425]: cannot find function `test123` in crate `utils`
--> src/main.rs:4:12
|
4 | utils::test123(); // ??? - does not work
| ^^^^^^^ not found in `utils`
error: aborting due to previous error
For more information about this error, try `rustc --explain E0425`.
error: could not compile `rust_test`.
I think that getting rid of mod utils; in main.rs should
solve your problem.
mod utils; in main.rs tells the compiler that
utils is an inner module of your application (but it
does not exist so does not contain the functions you are
looking for), although it is actually a crate (external
to your application).
The module system helps organise the details inside a crate
while a crate is seen as a library.
edit
You should also get rid of #[cfg(utils)] in lib.rs because
it means that the following item exists only if the utils
feature is set in your Cargo.toml file (which is not
the case).
The cfg() directives are intended for conditional compilation.
( https://doc.rust-lang.org/reference/conditional-compilation.html )
And sorry, I forgot, mod utils {} in lib.rs may not be necessary,
or you will need to refer to the function as utils::utils::test123()
from your application.
The first utils refers to the crate, the second utils refers to
an inner module of this crate.
In build.rs of level1-sys crate I have:
let dst = cmake::Config::new(Path::new("somelib"))
.build()
.join("build");
println!("cargo:rustc-link-search=native={}", dst.display());
println!("cargo:rustc-link-lib=dylib=somelib");
then there is level2 create that deped on level1-sys,
and then there is level3binary crate.
If I run this level3 crates via cargo run all works fine,
but if I run it by hands it reports:
error while loading shared libraries: libsomelib.so: cannot open shared object file: No such file or directory
Is there way to find path to libsomelib.so from cargo?
I need this info for external script that should pack binary.
Obviously I can search in target subdirectory,
but I use debug/release/cross compilation and so on thing.
Plus even for concrete variant like target/release after several rebuild of level1-sys there are several libsomelib.so libraries, like:
target/release/build/level1-sys-46422ddc8585ba79/libsomelib.so
target/release/build/level1-sys-9daa760ee41fe7b8/libsomelib.so
This question already has answers here:
How to disable unused code warnings in Rust?
(11 answers)
Closed 3 years ago.
I have a Rust project folder structure that contains an executable and a shared C-compatible library that are both build using the same sources. The Cargo.toml manifest file looks like:
[package]
name = "foo-bar"
version = "0.1.0"
authors = ...
[lib]
name = "foo_bar"
crate-type = ["rlib", "cdylib"]
[[bin]]
name = "foo-bar"
test = false
doc = false
[dependencies]
...
As the executable is not using all of the code I get some "unused code" warnings when building the project with cargo build. I could add #[allow(dead_code)] lints all over my source code where necessary but that would disable them also when building the library target.
Is there a way to globally disable the "dead_code" lint only when compiling the (feature-wise smaller) bin executable target but having it enabled for the lib target?
You can modify a lint for a whole crate by putting an attribute with #! at the beginning of the crate:
main.rs:
#![allow(dead_code)]
// etc.
I have a binary Rust project which uses the workspaces to manage sub-crates.
Directory structure
/myapp
Cargo.toml
/src
/tests
test.rs
/crates
/printer
Cargo.toml
/src
myapp/Cargo.toml
[package]
name = "myapp"
[workspace]
members = ["crates/printer"]
Inside of test.rs I can compile extern crate myapp; to pull in the parts of the application that are exposed in src/lib.rs. This works as expected.
However, when attempting to compile extern crate printer; it errors that it cannot find it. I've confirmed that the printer package is correctly placed in the top-level Cargo.lock file.
How do I include my sub-crates into the /tests directory at the top level?
There's nothing special about workspaces or even the concept of tests. If you want to use a crate in Rust code, you have to add it as a dependency:
[dependencies]
printer = { path = "crates/printer" }
See also:
How to define test-only dependencies?
I have a crate with both src/lib.rs and src/main.rs.
main.rs is just using extern crate programname (which is lib.rs) and uses certain functions from lib.rs and it's submodules.
The documentation on linking says:
Pure-Rust dependencies are statically linked by default so you can use created binaries and libraries without installing Rust everywhere.
How can I change this behavior so a binary created from main.rs will be dynamically linked to library produced by lib.rs?
I've added the following to Cargo.toml
[lib]
path = "src/lib.rs"
crate-type = ["dylib"]
[[bin]]
name = "programname"
path = "src/main.rs"
But it does not compile and gives me errors like:
error: cannot satisfy dependencies so `std` only shows up once
help: having upstream crates all available in one format will likely make this go away
If I add "rlib" to lib section, it compiles, but the binary is not linked against libprogramname.so