I have a rust application that I wish to link against a few C++ static libraries. I have my build.rs script triggering the compilation of my C++ libraries which I then link using a cargo command:
println!("cargo:rustc-link-lib=static={}", lib);
If I link the release version of my static libraries, everything works as expected and the build passes without errors. However, on a debug profile of my rust application, I tried linking the debug version of my libraries, which in turn try to link the debug version of the crt. This causes multiple linker errors:
- the debug static libraries require the debug version of the crt, and can't find it:
fmtd.lib(format.cc.obj) : error LNK2001: unresolved external symbol __imp__CrtDbgReport
- there is a mismatch between some rust libraries and the C++ libraries with respect to the CRT:
ccore.lib(ccore.obj) : error LNK2038: mismatch detected for 'RuntimeLibrary': value 'MDd_DynamicDebug' doesn't match value 'MD_DynamicRelease' in libcxx-6a7727867c21870c.rlib(15a3702a9d40a852-cxx.o)
I tried to resolve the issues by somehow forcing rust to link the debug version of the CRT:
// Don't link the default CRT
println!("cargo::rustc-link-arg=/nodefaultlib:msvcrt");
// Link the debug CRT instead
println!("cargo::rustc-link-arg=/defaultlib:msvcrtd");
Now the C++ libraries can find the crt (resolves the first issue) but the mismatch remains. My assumption is the the rust cargo dependencies (libcxx in this case) still require the release version of the CRT.
I also tried to somehow force the correct version of the autogenerated cxx crate glue:
let mut bridge = cxx_build::bridge("src/lib.rs");
bridge.include(&ccore_include);
bridge.include(&vcpkg_installed_include_dir);
// bridge.debug(true); // <-- important, picks /MDd in debug builds
bridge.flag("/Zl");
bridge.flag("/MDd"); // force dynamic debug runtime
bridge.compile("app-cxx-bridge");
But it did not help.
Most of the solutions I came up with can be found on the following github issues:
rustc always links against non-debug Windows runtime
So How can I configure a rust application to link against the correct version of the CRT?
__impmeans it needs to link to an import library for a dll.