Let's say I have two crate in my project, crate mangle2 depends on crate mangle1 and they are located in directory1.
root -> /usr1/directory1 $ tree
.
├── mangle1
│ ├── Cargo.toml
│ └── src
│ └── lib.rs
└── mangle2
├── Cargo.toml
└── src
└── lib.rs
in mangle2/Cargo.toml file, we see mangle2 depends on mangle1.
[package]
name = "mangle2"
version = "0.1.0"
edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
mangle1 = { path = "../mangle1" }
I define a simple function in the mangle1 directory and reference it in mangle2.
Then I went into the mangle2 directory and compiled the whole project.
root -> /usr1/directory1 $ cd mangle2
root -> /usr1/directory1/mangle2 $ cargo build
Compiling mangle1 v0.1.0 (/usr1/s00659936/rust_program/mangle_disambiguator_test/test2/mangle1)
Compiling mangle2 v0.1.0 (/usr1/s00659936/rust_program/mangle_disambiguator_test/test2/mangle2)
Finished dev [unoptimized + debuginfo] target(s) in 0.19s
We use the readelf command to see the name of the symbol table.
root -> /usr1/directory1/mangle2 $ readelf -sW target/debug/libmangle2.rlib
.....
Symbol table '.symtab' contains 19 entries:
Num: Value Size Type Bind Vis Ndx Name
0: 0000000000000000 0 NOTYPE LOCAL DEFAULT UND
......
17: 0000000000000000 32 FUNC GLOBAL DEFAULT 3 _ZN7mangle29super_add17h9e7d5740a4187474E
18: 0000000000000000 0 NOTYPE GLOBAL DEFAULT UND _ZN7mangle16sjhadd17h565c9c31ddc83d00E
Then I copied the directory1 directory to another location directory2.
root -> /usr1 $ cp directory1 directory2 -rf
root -> /usr1 $ cd directory2
root -> /usr1/directory2 $ tree
.
├── mangle1
│ ├── Cargo.toml
│ └── src
│ └── lib.rs
└── mangle2
├── Cargo.toml
└── src
└── lib.rs
As before, I went into the mangle2 directory and compiled the whole project.
root -> /usr1/directory2/mangle2 $ readelf -sW target/debug/libmangle2.rlib
.....
Symbol table '.symtab' contains 19 entries:
Num: Value Size Type Bind Vis Ndx Name
0: 0000000000000000 0 NOTYPE LOCAL DEFAULT UND
......
17: 0000000000000000 32 FUNC GLOBAL DEFAULT 3 _ZN7mangle29super_add17hc8831168e2d1a643E
18: 0000000000000000 0 NOTYPE GLOBAL DEFAULT UND _ZN7mangle16sjhadd17h1484bdaf46e8f547E
As you can see, the name of the generating function has changed, and the last string of 17 hashes has changed.
_ZN7mangle29super_add17h9e7d5740a4187474E change to _ZN7mangle29super_add17hc8831168e2d1a643E
I didn't change a single line of code, and I cleaned up the build artifacts, including Cargo.lock, before compiling. Why is the resulting binary inconsistent?
If a single crate is copied to another directory for compilation, this problem does not occur. Binary inconsistency occurs when two crates depend on each other and both crates are copied to another directory.