Auto merge of #24448 - alexcrichton:issue-24445, r=huonw

One of the parameters to the magical "register a thread-local destructor"
function is called `__dso_handle` and largely just passed along (this seems to
be what other implementations do). Currently we pass the *value* of this symbol,
but apparently the correct piece of information to pass is the *address* of the
symbol.

In a PIE binary the symbol actually contains an address to itself which is why
we've gotten away with what we're doing as long as we have. In a non-PIE binary
the symbol contains the address `NULL`, causing a segfault in the runtime
library if it keeps going.

Closes #24445
This commit is contained in:
bors 2015-04-16 13:29:52 +00:00
commit 5576b0558c
4 changed files with 54 additions and 1 deletions

View File

@ -373,7 +373,7 @@ mod imp {
arg: *mut u8,
dso_handle: *mut u8) -> libc::c_int;
mem::transmute::<*const (), F>(__cxa_thread_atexit_impl)
(dtor, t, __dso_handle);
(dtor, t, &__dso_handle as *const _ as *mut _);
return
}

View File

@ -0,0 +1,12 @@
-include ../tools.mk
ifeq ($(UNAME),Linux)
all:
$(RUSTC) foo.rs
$(CC) foo.c -lfoo -L $(TMPDIR) -Wl,--gc-sections -lpthread -o $(TMPDIR)/foo
$(call RUN,foo)
$(CC) foo.c -lfoo -L $(TMPDIR) -Wl,--gc-sections -lpthread -pie -fPIC -o $(TMPDIR)/foo
$(call RUN,foo)
else
all:
endif

View File

@ -0,0 +1,16 @@
// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
void foo();
int main() {
foo();
return 0;
}

View File

@ -0,0 +1,25 @@
// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.
#![crate_type = "staticlib"]
struct Destroy;
impl Drop for Destroy {
fn drop(&mut self) { println!("drop"); }
}
thread_local! {
static X: Destroy = Destroy
}
#[no_mangle]
pub extern "C" fn foo() {
X.with(|_| ());
}