Skip to content

Commit a18772a

Browse files
committed
use --dynamic-list for exporting executable symbols
1 parent 556d20a commit a18772a

File tree

2 files changed

+47
-0
lines changed

2 files changed

+47
-0
lines changed

compiler/rustc_codegen_ssa/src/back/linker.rs

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -835,6 +835,22 @@ impl<'a> Linker for GccLinker<'a> {
835835
if let Err(error) = res {
836836
self.sess.dcx().emit_fatal(errors::LibDefWriteFailure { error });
837837
}
838+
} else if crate_type == CrateType::Executable {
839+
// Write an LD version script
840+
let res: io::Result<()> = try {
841+
let mut f = File::create_buffered(&path)?;
842+
writeln!(f, "{{")?;
843+
if !symbols.is_empty() {
844+
for (sym, _) in symbols {
845+
debug!(" {sym};");
846+
writeln!(f, " {sym};")?;
847+
}
848+
}
849+
writeln!(f, "}};")?;
850+
};
851+
if let Err(error) = res {
852+
self.sess.dcx().emit_fatal(errors::VersionScriptWriteFailure { error });
853+
}
838854
} else {
839855
// Write an LD version script
840856
let res: io::Result<()> = try {
@@ -860,6 +876,8 @@ impl<'a> Linker for GccLinker<'a> {
860876
self.link_arg("-M").link_arg(path);
861877
} else if is_windows {
862878
self.link_arg(path);
879+
} else if crate_type == CrateType::Executable {
880+
self.link_arg("--dynamic-list").link_arg(path);
863881
} else {
864882
let mut arg = OsString::from("--version-script=");
865883
arg.push(path);
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
//@ run-pass
2+
//@ only-linux
3+
//@ compile-flags: -Zexport-executable-symbols
4+
//@ edition: 2024
5+
6+
// Regression test for <https://github.com/rust-lang/rust/issues/101610>.
7+
8+
#![feature(rustc_private)]
9+
10+
extern crate libc;
11+
12+
#[unsafe(no_mangle)]
13+
fn hack() -> u64 {
14+
998244353
15+
}
16+
17+
fn main() {
18+
unsafe {
19+
let handle = libc::dlopen(std::ptr::null(), libc::RTLD_NOW);
20+
let ptr = libc::dlsym(handle, c"hack".as_ptr());
21+
let ptr: Option<unsafe fn() -> u64> = std::mem::transmute(ptr);
22+
if let Some(f) = ptr {
23+
assert!(f() == 998244353);
24+
println!("symbol `hack` is found successfully");
25+
} else {
26+
panic!("symbol `hack` is not found");
27+
}
28+
}
29+
}

0 commit comments

Comments
 (0)