about summary refs log tree commit diff
path: root/src/libstd/task
diff options
context:
space:
mode:
authorAlex Crichton <alex@alexcrichton.com>2013-07-14 01:43:31 -0700
committerAlex Crichton <alex@alexcrichton.com>2013-07-14 10:15:07 -0700
commit9fd2ac7428afa4f414f32b8b4876ca817ee85f16 (patch)
treed95eb9acc27f980f2365330b3aa9566e8eec2010 /src/libstd/task
parente3211fa1f1f24268b91b0c89cb312e70499d41f3 (diff)
downloadrust-9fd2ac7428afa4f414f32b8b4876ca817ee85f16.tar.gz
rust-9fd2ac7428afa4f414f32b8b4876ca817ee85f16.zip
Make TLS keys actually take up space
If the TLS key is 0-sized, then the linux linker is apparently smart enough to
put everything at the same pointer. OSX on the other hand, will reserve some
space for all of them. To get around this, the TLS key now actuall consumes
space to ensure that it gets a unique pointer
Diffstat (limited to 'src/libstd/task')
-rw-r--r--src/libstd/task/local_data_priv.rs3
-rw-r--r--src/libstd/task/spawn.rs19
2 files changed, 13 insertions, 9 deletions
diff --git a/src/libstd/task/local_data_priv.rs b/src/libstd/task/local_data_priv.rs
index 1a2141e996a..d46e5707f14 100644
--- a/src/libstd/task/local_data_priv.rs
+++ b/src/libstd/task/local_data_priv.rs
@@ -17,7 +17,6 @@ use prelude::*;
 use ptr;
 use task::rt;
 use util;
-use vec;
 
 use super::rt::rust_task;
 use rt::task::{Task, LocalStorage};
@@ -143,7 +142,7 @@ unsafe fn get_local_map(handle: Handle) -> &mut TaskLocalMap {
 }
 
 fn key_to_key_value<T: 'static>(key: local_data::Key<T>) -> *libc::c_void {
-    return vec::raw::to_ptr(key) as *libc::c_void;
+    unsafe { cast::transmute(key) }
 }
 
 pub unsafe fn local_pop<T: 'static>(handle: Handle,
diff --git a/src/libstd/task/spawn.rs b/src/libstd/task/spawn.rs
index 27cb1c2c100..206d19e175f 100644
--- a/src/libstd/task/spawn.rs
+++ b/src/libstd/task/spawn.rs
@@ -80,6 +80,7 @@ use cell::Cell;
 use container::MutableMap;
 use comm::{Chan, GenericChan};
 use hashmap::HashSet;
+use local_data;
 use task::local_data_priv::{local_get, local_set, OldHandle};
 use task::rt::rust_task;
 use task::rt;
@@ -465,10 +466,14 @@ fn kill_taskgroup(state: TaskGroupInner, me: *rust_task, is_main: bool) {
 
 // FIXME (#2912): Work around core-vs-coretest function duplication. Can't use
 // a proper closure because the #[test]s won't understand. Have to fake it.
-macro_rules! taskgroup_key (
-    // Use a "code pointer" value that will never be a real code pointer.
-    () => (cast::transmute((-2 as uint, 0u)))
-)
+#[cfg(not(stage0))]
+fn taskgroup_key() -> local_data::Key<@@mut TCB> {
+    unsafe { cast::transmute(-2) }
+}
+#[cfg(stage0)]
+fn taskgroup_key() -> local_data::Key<@@mut TCB> {
+    unsafe { cast::transmute((-2, 0)) }
+}
 
 fn gen_child_taskgroup(linked: bool, supervised: bool)
     -> (TaskGroupArc, AncestorList, bool) {
@@ -478,7 +483,7 @@ fn gen_child_taskgroup(linked: bool, supervised: bool)
          * Step 1. Get spawner's taskgroup info.
          *##################################################################*/
         let spawner_group: @@mut TCB =
-            do local_get(OldHandle(spawner), taskgroup_key!()) |group| {
+            do local_get(OldHandle(spawner), taskgroup_key()) |group| {
                 match group {
                     None => {
                         // Main task, doing first spawn ever. Lazily initialise
@@ -495,7 +500,7 @@ fn gen_child_taskgroup(linked: bool, supervised: bool)
                                               AncestorList(None),
                                               true,
                                               None);
-                        local_set(OldHandle(spawner), taskgroup_key!(), group);
+                        local_set(OldHandle(spawner), taskgroup_key(), group);
                         group
                     }
                     Some(&group) => group
@@ -688,7 +693,7 @@ fn spawn_raw_oldsched(mut opts: TaskOpts, f: ~fn()) {
                                       is_main,
                                       notifier);
                 unsafe {
-                    local_set(OldHandle(child), taskgroup_key!(), group);
+                    local_set(OldHandle(child), taskgroup_key(), group);
                 }
 
                 // Run the child's body.