diff --git a/src/doc/rustc/src/codegen-options/index.md b/src/doc/rustc/src/codegen-options/index.md index 0dc81378e05b2..e543886ebd9cb 100644 --- a/src/doc/rustc/src/codegen-options/index.md +++ b/src/doc/rustc/src/codegen-options/index.md @@ -203,6 +203,13 @@ for determining whether or not it is possible to statically or dynamically link with a dependency. For example, `cdylib` crate types may only use static linkage. +## export-executable-symbols + +This flag causes `rustc` to export symbols from executables, as if they were dynamic libraries. + +You might use this to allow the JVM or MSCLR to call back into your executable's +Rust code from Java/C# when embedding their runtimes into your Rust executable. + ## no-integrated-as `rustc` normally uses the LLVM internal assembler to create object code. This diff --git a/src/librustc_codegen_ssa/back/linker.rs b/src/librustc_codegen_ssa/back/linker.rs index a3e60f861996a..afee3db11483f 100644 --- a/src/librustc_codegen_ssa/back/linker.rs +++ b/src/librustc_codegen_ssa/back/linker.rs @@ -421,6 +421,7 @@ impl<'a> Linker for GccLinker<'a> { // Symbol visibility in object files typically takes care of this. if crate_type == CrateType::Executable && self.sess.target.target.options.override_export_symbols.is_none() + && !self.sess.opts.cg.export_executable_symbols { return; } @@ -699,10 +700,14 @@ impl<'a> Linker for MsvcLinker<'a> { // their symbols exported. fn export_symbols(&mut self, tmpdir: &Path, crate_type: CrateType) { // Symbol visibility takes care of this typically - if crate_type == CrateType::Executable { + if crate_type == CrateType::Executable + && !self.sess.opts.cg.export_executable_symbols + { return; } + debug!("EXPORTED SYMBOLS:"); + let path = tmpdir.join("lib.def"); let res: io::Result<()> = try { let mut f = BufWriter::new(File::create(&path)?); @@ -712,7 +717,7 @@ impl<'a> Linker for MsvcLinker<'a> { writeln!(f, "LIBRARY")?; writeln!(f, "EXPORTS")?; for symbol in self.info.exports[&crate_type].iter() { - debug!(" _{}", symbol); + debug!(" {}", symbol); writeln!(f, " {}", symbol)?; } }; diff --git a/src/librustc_session/options.rs b/src/librustc_session/options.rs index 38c17bbbde797..b96268b6fe859 100644 --- a/src/librustc_session/options.rs +++ b/src/librustc_session/options.rs @@ -652,6 +652,8 @@ options! {CodegenOptions, CodegenSetter, basic_codegen_options, "use soft float ABI (*eabihf targets only)"), prefer_dynamic: bool = (false, parse_bool, [TRACKED], "prefer dynamic linking to static linking"), + export_executable_symbols: bool = (false, parse_bool, [UNTRACKED], + "export symbols from executables, as if they were dynamic libraries"), no_integrated_as: bool = (false, parse_bool, [TRACKED], "use an external assembler rather than LLVM's integrated one"), no_redzone: Option = (None, parse_opt_bool, [TRACKED],