Suppress ``link-arg`` in dependency

I’m building a library for FFI users that depends on a sibling library
which is also available through FFI. To illustrate the project layout:

├── dependency
│   ├──
│   ├── Cargo.toml
│   └── src
│       └──
└── main
    ├── Cargo.toml
    └── src

Here both main and dependency are libraries of crate-type = ["lib", "cdylib"].
(In the actual product they’re part of a workspace but the problem
occurs without a workspace as well so let’s not complicate matters.)

main depends on dependency like so:

dependency = { path = "../dependency" }

dependency is a leaf library. Both main and dependency get
their DT_SONAME embedded like so:

$ cat dependency/
fn main () { println!("cargo:rustc-cdylib-link-arg=-Wl,-soname,"); }
$ cat main/
fn main () { println!("cargo:rustc-cdylib-link-arg=-Wl,-soname,"); }

(Actually I’m using the cdylib-link-lines crate to accomplish this
but it boils down to the same issue.)

This works fine for However, when running
cargo run in ./main/, I obtain a with the
SONAME of embedded

$ readelf -d target/debug/ |grep SONAME
 0x000000000000000e (SONAME)             Library soname: []

This is obviously wrong, it should be :wink: The reason
for this is that the rustc-cdylib-link-arg lines get executed from
the of both libraries. Thus both of them end up
getting appended to the rustc command line:

rustc \
    --crate-name main \
    --edition=2021 src/ \
    --error-format=json \
    --json=diagnostic-rendered-ansi,artifacts,future-incompat \
    --crate-type lib \
    --crate-type cdylib \
    --emit=dep-info,link \
    -C embed-bitcode=no \
    -C debuginfo=2 \
    -C metadata=e0d0d2eeaf7bb2d0 \
    --out-dir /home/phg/src/ugh-cargo/soname/main/target/debug/deps \
    -C incremental=/home/phg/src/ugh-cargo/soname/main/target/debug/incremental \
    -L dependency=/home/phg/src/ugh-cargo/soname/main/target/debug/deps \
    --extern dependency=/home/phg/src/ugh-cargo/soname/main/target/debug/deps/libdependency.rlib \
    -C link-arg=-Wl,-soname, \
    -C link-arg=-Wl,-soname,

Now since there is only one SONAME field per object file, this
would actually work if the order of link-args were reversed. As
it is, later arguments override earlier ones and bam,
wrongly claims it’s!

Ideally Cargo would support setting the SONAME directly in

Alternatively, I’d be happy with a mechanism to suppress the bad -C link-arg in the above example when building However,
conditionally disabling the println! in dependency/
results in the SONAME being missing from
Is there a way to filter rustc arguments added by dependencies?

I guess if I could tell cargo to put the output of main/
last, that would work too.

FWIW I also tried adding to the linker line in .cargo/config.toml
but the values there get prepended to those from

EDIT: So do arguments to cargo on the command line (--config='build.rustflags = [ "-C", "link-arg=-Wl,-soname," ]').

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.