Skip to content

Commit 1c35ab3

Browse files
committed
auto merge of #7751 : alexcrichton/rust/finish-tls, r=pcwalton
This changes the interface to `get`, and it also changes the keys to be static slices instead of static functions. This allows the removal of the `unsafe` interface because while functions can monomorphize from different types to the same actual function, static slices cannot do this. From at least what I can tell, we don't need to worry about LLVM coalescing these addresses. If we ever use the `unnamed_addr` it looks like there's cause for worry, but there doesn't appear to be any coalescing atm.
2 parents 66e2857 + 9fd2ac7 commit 1c35ab3

26 files changed

+357
-349
lines changed

src/libextra/rl.rs

Lines changed: 15 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -66,24 +66,28 @@ pub unsafe fn read(prompt: &str) -> Option<~str> {
6666
}
6767
}
6868

69-
pub type CompletionCb<'self> = @fn(~str, &'self fn(~str));
69+
pub type CompletionCb = @fn(~str, @fn(~str));
7070

71-
fn complete_key(_v: @CompletionCb) {}
71+
#[cfg(not(stage0))]
72+
static complete_key: local_data::Key<@CompletionCb> = &local_data::Key;
73+
#[cfg(stage0)]
74+
fn complete_key(_: @CompletionCb) {}
7275

7376
/// Bind to the main completion callback
7477
pub unsafe fn complete(cb: CompletionCb) {
75-
local_data::set(complete_key, @(cb));
78+
local_data::set(complete_key, @cb);
7679

7780
extern fn callback(line: *c_char, completions: *()) {
78-
unsafe {
79-
let cb = *local_data::get(complete_key, |k| k.map(|&k| *k))
80-
.get();
81-
82-
do cb(str::raw::from_c_str(line)) |suggestion| {
83-
do str::as_c_str(suggestion) |buf| {
84-
rustrt::linenoiseAddCompletion(completions, buf);
81+
do local_data::get(complete_key) |cb| {
82+
let cb = **cb.unwrap();
83+
84+
unsafe {
85+
do cb(str::raw::from_c_str(line)) |suggestion| {
86+
do str::as_c_str(suggestion) |buf| {
87+
rustrt::linenoiseAddCompletion(completions, buf);
88+
}
8589
}
86-
}
90+
}
8791
}
8892
}
8993

src/libextra/sort.rs

Lines changed: 0 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -1195,39 +1195,4 @@ mod big_tests {
11951195
isSorted(arr);
11961196
}
11971197
}
1198-
1199-
struct LVal<'self> {
1200-
val: uint,
1201-
key: &'self fn:Copy(@uint),
1202-
}
1203-
1204-
#[unsafe_destructor]
1205-
impl<'self> Drop for LVal<'self> {
1206-
fn drop(&self) {
1207-
let x = unsafe { local_data::get(self.key, |k| k.map(|&k| *k)) };
1208-
match x {
1209-
Some(@y) => {
1210-
unsafe {
1211-
local_data::set(self.key, @(y+1));
1212-
}
1213-
}
1214-
_ => fail!("Expected key to work"),
1215-
}
1216-
}
1217-
}
1218-
1219-
impl<'self> Ord for LVal<'self> {
1220-
fn lt<'a>(&self, other: &'a LVal<'self>) -> bool {
1221-
(*self).val < other.val
1222-
}
1223-
fn le<'a>(&self, other: &'a LVal<'self>) -> bool {
1224-
(*self).val <= other.val
1225-
}
1226-
fn gt<'a>(&self, other: &'a LVal<'self>) -> bool {
1227-
(*self).val > other.val
1228-
}
1229-
fn ge<'a>(&self, other: &'a LVal<'self>) -> bool {
1230-
(*self).val >= other.val
1231-
}
1232-
}
12331198
}

src/librustc/back/link.rs

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,7 @@ pub mod jit {
105105
use metadata::cstore;
106106

107107
use std::cast;
108+
#[cfg(not(stage0))]
108109
use std::local_data;
109110
use std::unstable::intrinsics;
110111

@@ -202,18 +203,19 @@ pub mod jit {
202203

203204
// The stage1 compiler won't work, but that doesn't really matter. TLS
204205
// changed only very recently to allow storage of owned values.
205-
fn engine_key(_: ~Engine) {}
206+
#[cfg(not(stage0))]
207+
static engine_key: local_data::Key<~Engine> = &local_data::Key;
206208

207209
#[cfg(not(stage0))]
208210
fn set_engine(engine: ~Engine) {
209-
unsafe { local_data::set(engine_key, engine) }
211+
local_data::set(engine_key, engine)
210212
}
211213
#[cfg(stage0)]
212214
fn set_engine(_: ~Engine) {}
213215

214216
#[cfg(not(stage0))]
215217
pub fn consume_engine() -> Option<~Engine> {
216-
unsafe { local_data::pop(engine_key) }
218+
local_data::pop(engine_key)
217219
}
218220
#[cfg(stage0)]
219221
pub fn consume_engine() -> Option<~Engine> { None }

src/librustc/middle/lint.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -209,7 +209,7 @@ static lint_table: &'static [(&'static str, LintSpec)] = &[
209209
LintSpec {
210210
lint: non_uppercase_statics,
211211
desc: "static constants should have uppercase identifiers",
212-
default: warn
212+
default: allow
213213
}),
214214

215215
("managed_heap_memory",

src/librustc/middle/trans/base.rs

Lines changed: 19 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -87,49 +87,44 @@ use syntax::abi::{X86, X86_64, Arm, Mips};
8787

8888
pub use middle::trans::context::task_llcx;
8989

90-
fn task_local_insn_key(_v: @~[&'static str]) {}
90+
#[cfg(not(stage0))]
91+
static task_local_insn_key: local_data::Key<@~[&'static str]> = &local_data::Key;
92+
#[cfg(stage0)]
93+
fn task_local_insn_key(_: @~[&'static str]) {}
9194

9295
pub fn with_insn_ctxt(blk: &fn(&[&'static str])) {
93-
unsafe {
94-
let opt = local_data::get(task_local_insn_key, |k| k.map(|&k| *k));
95-
if opt.is_some() {
96-
blk(*opt.unwrap());
97-
}
96+
let opt = local_data::get(task_local_insn_key, |k| k.map(|&k| *k));
97+
if opt.is_some() {
98+
blk(*opt.unwrap());
9899
}
99100
}
100101

101102
pub fn init_insn_ctxt() {
102-
unsafe {
103-
local_data::set(task_local_insn_key, @~[]);
104-
}
103+
local_data::set(task_local_insn_key, @~[]);
105104
}
106105

107106
pub struct _InsnCtxt { _x: () }
108107

109108
#[unsafe_destructor]
110109
impl Drop for _InsnCtxt {
111110
fn drop(&self) {
112-
unsafe {
113-
do local_data::modify(task_local_insn_key) |c| {
114-
do c.map_consume |ctx| {
115-
let mut ctx = copy *ctx;
116-
ctx.pop();
117-
@ctx
118-
}
111+
do local_data::modify(task_local_insn_key) |c| {
112+
do c.map_consume |ctx| {
113+
let mut ctx = copy *ctx;
114+
ctx.pop();
115+
@ctx
119116
}
120117
}
121118
}
122119
}
123120

124121
pub fn push_ctxt(s: &'static str) -> _InsnCtxt {
125122
debug!("new InsnCtxt: %s", s);
126-
unsafe {
127-
do local_data::modify(task_local_insn_key) |c| {
128-
do c.map_consume |ctx| {
129-
let mut ctx = copy *ctx;
130-
ctx.push(s);
131-
@ctx
132-
}
123+
do local_data::modify(task_local_insn_key) |c| {
124+
do c.map_consume |ctx| {
125+
let mut ctx = copy *ctx;
126+
ctx.push(s);
127+
@ctx
133128
}
134129
}
135130
_InsnCtxt { _x: () }
@@ -1428,7 +1423,7 @@ pub fn with_scope(bcx: block,
14281423

14291424
pub fn with_scope_result(bcx: block,
14301425
opt_node_info: Option<NodeInfo>,
1431-
name: &str,
1426+
_name: &str,
14321427
f: &fn(block) -> Result) -> Result {
14331428
let _icx = push_ctxt("with_scope_result");
14341429

src/librustc/middle/trans/callee.rs

Lines changed: 8 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -197,7 +197,7 @@ fn get_impl_resolutions(bcx: block,
197197
impl_id: ast::def_id)
198198
-> typeck::vtable_res {
199199
if impl_id.crate == ast::local_crate {
200-
*bcx.ccx().maps.vtable_map.get(&impl_id.node)
200+
bcx.ccx().maps.vtable_map.get_copy(&impl_id.node)
201201
} else {
202202
// XXX: This is a temporary hack to work around not properly
203203
// exporting information about resolutions for impls.
@@ -670,15 +670,13 @@ pub fn trans_call_inner(in_cx: block,
670670
None => { assert!(ty::type_is_immediate(bcx.tcx(), ret_ty)) }
671671
Some(expr::Ignore) => {
672672
// drop the value if it is not being saved.
673-
unsafe {
674-
if ty::type_needs_drop(bcx.tcx(), ret_ty) {
675-
if ty::type_is_immediate(bcx.tcx(), ret_ty) {
676-
let llscratchptr = alloc_ty(bcx, ret_ty, "__ret");
677-
Store(bcx, llresult, llscratchptr);
678-
bcx = glue::drop_ty(bcx, llscratchptr, ret_ty);
679-
} else {
680-
bcx = glue::drop_ty(bcx, llretslot, ret_ty);
681-
}
673+
if ty::type_needs_drop(bcx.tcx(), ret_ty) {
674+
if ty::type_is_immediate(bcx.tcx(), ret_ty) {
675+
let llscratchptr = alloc_ty(bcx, ret_ty, "__ret");
676+
Store(bcx, llresult, llscratchptr);
677+
bcx = glue::drop_ty(bcx, llscratchptr, ret_ty);
678+
} else {
679+
bcx = glue::drop_ty(bcx, llretslot, ret_ty);
682680
}
683681
}
684682
}

src/librustc/middle/trans/context.rs

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -232,22 +232,24 @@ impl CrateContext {
232232
#[unsafe_destructor]
233233
impl Drop for CrateContext {
234234
fn drop(&self) {
235-
unsafe {
236-
unset_task_llcx();
237-
}
235+
unset_task_llcx();
238236
}
239237
}
240238

239+
#[cfg(stage0)]
241240
fn task_local_llcx_key(_v: @ContextRef) {}
241+
#[cfg(not(stage0))]
242+
static task_local_llcx_key: local_data::Key<@ContextRef> = &local_data::Key;
243+
242244
pub fn task_llcx() -> ContextRef {
243-
let opt = unsafe { local_data::get(task_local_llcx_key, |k| k.map(|&k| *k)) };
245+
let opt = local_data::get(task_local_llcx_key, |k| k.map(|&k| *k));
244246
*opt.expect("task-local LLVMContextRef wasn't ever set!")
245247
}
246248

247-
unsafe fn set_task_llcx(c: ContextRef) {
249+
fn set_task_llcx(c: ContextRef) {
248250
local_data::set(task_local_llcx_key, @c);
249251
}
250252

251-
unsafe fn unset_task_llcx() {
253+
fn unset_task_llcx() {
252254
local_data::pop(task_local_llcx_key);
253255
}

src/librustc/middle/trans/controlflow.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -254,7 +254,7 @@ pub fn trans_break_cont(bcx: block,
254254
// Locate closest loop block, outputting cleanup as we go.
255255
let mut unwind = bcx;
256256
let mut cur_scope = unwind.scope;
257-
let mut target = unwind;
257+
let mut target;
258258
loop {
259259
cur_scope = match cur_scope {
260260
Some(@scope_info {

src/librustc/middle/ty.rs

Lines changed: 20 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -3621,25 +3621,29 @@ pub fn trait_method_def_ids(cx: ctxt, id: ast::def_id) -> @~[def_id] {
36213621
}
36223622

36233623
pub fn impl_trait_ref(cx: ctxt, id: ast::def_id) -> Option<@TraitRef> {
3624-
*do cx.impl_trait_cache.find_or_insert_with(id) |_| {
3625-
if id.crate == ast::local_crate {
3626-
debug!("(impl_trait_ref) searching for trait impl %?", id);
3627-
match cx.items.find(&id.node) {
3628-
Some(&ast_map::node_item(@ast::item {
3629-
node: ast::item_impl(_, ref opt_trait, _, _),
3630-
_},
3631-
_)) => {
3632-
match opt_trait {
3633-
&Some(ref t) => Some(ty::node_id_to_trait_ref(cx, t.ref_id)),
3634-
&None => None
3635-
}
3624+
match cx.impl_trait_cache.find(&id) {
3625+
Some(&ret) => { return ret; }
3626+
None => {}
3627+
}
3628+
let ret = if id.crate == ast::local_crate {
3629+
debug!("(impl_trait_ref) searching for trait impl %?", id);
3630+
match cx.items.find(&id.node) {
3631+
Some(&ast_map::node_item(@ast::item {
3632+
node: ast::item_impl(_, ref opt_trait, _, _),
3633+
_},
3634+
_)) => {
3635+
match opt_trait {
3636+
&Some(ref t) => Some(ty::node_id_to_trait_ref(cx, t.ref_id)),
3637+
&None => None
36363638
}
3637-
_ => None
36383639
}
3639-
} else {
3640-
csearch::get_impl_trait(cx, id)
3640+
_ => None
36413641
}
3642-
}
3642+
} else {
3643+
csearch::get_impl_trait(cx, id)
3644+
};
3645+
cx.impl_trait_cache.insert(id, ret);
3646+
return ret;
36433647
}
36443648

36453649
pub fn ty_to_def_id(ty: t) -> Option<ast::def_id> {

src/librustc/middle/typeck/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -303,7 +303,7 @@ fn check_main_fn_ty(ccx: &CrateCtxt,
303303
let tcx = ccx.tcx;
304304
let main_t = ty::node_id_to_type(tcx, main_id);
305305
match ty::get(main_t).sty {
306-
ty::ty_bare_fn(ref fn_ty) => {
306+
ty::ty_bare_fn(*) => {
307307
match tcx.items.find(&main_id) {
308308
Some(&ast_map::node_item(it,_)) => {
309309
match it.node {

src/librustc/rustc.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,6 @@
1818
#[crate_type = "lib"];
1919

2020
#[allow(non_implicitly_copyable_typarams)];
21-
#[allow(non_camel_case_types)];
22-
#[allow(non_uppercase_statics)];
2321
#[deny(deprecated_pattern)];
2422

2523
extern mod extra;

src/librusti/program.rs

Lines changed: 6 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@
1111
use std::cast;
1212
use std::hashmap::HashMap;
1313
use std::local_data;
14-
use std::sys;
1514

1615
use syntax::ast;
1716
use syntax::parse::token;
@@ -58,7 +57,7 @@ struct LocalVariable {
5857
}
5958

6059
type LocalCache = @mut HashMap<~str, @~[u8]>;
61-
fn tls_key(_k: LocalCache) {}
60+
static tls_key: local_data::Key<LocalCache> = &local_data::Key;
6261

6362
impl Program {
6463
pub fn new() -> Program {
@@ -131,21 +130,16 @@ impl Program {
131130
fn main() {
132131
");
133132

134-
let key: sys::Closure = unsafe {
135-
let tls_key: &'static fn(LocalCache) = tls_key;
136-
cast::transmute(tls_key)
137-
};
133+
let key: uint= unsafe { cast::transmute(tls_key) };
138134
// First, get a handle to the tls map which stores all the local
139135
// variables. This works by totally legitimately using the 'code'
140136
// pointer of the 'tls_key' function as a uint, and then casting it back
141137
// up to a function
142138
code.push_str(fmt!("
143139
let __tls_map: @mut ::std::hashmap::HashMap<~str, @~[u8]> = unsafe {
144-
let key = ::std::sys::Closure{ code: %? as *(),
145-
env: ::std::ptr::null() };
146-
let key = ::std::cast::transmute(key);
140+
let key = ::std::cast::transmute(%u);
147141
::std::local_data::get(key, |k| k.map(|&x| *x)).unwrap()
148-
};\n", key.code as uint));
142+
};\n", key as uint));
149143

150144
// Using this __tls_map handle, deserialize each variable binding that
151145
// we know about
@@ -226,18 +220,14 @@ impl Program {
226220
for self.local_vars.iter().advance |(name, value)| {
227221
map.insert(copy *name, @copy value.data);
228222
}
229-
unsafe {
230-
local_data::set(tls_key, map);
231-
}
223+
local_data::set(tls_key, map);
232224
}
233225

234226
/// Once the program has finished running, this function will consume the
235227
/// task-local cache of local variables. After the program finishes running,
236228
/// it updates this cache with the new values of each local variable.
237229
pub fn consume_cache(&mut self) {
238-
let map = unsafe {
239-
local_data::pop(tls_key).expect("tls is empty")
240-
};
230+
let map = local_data::pop(tls_key).expect("tls is empty");
241231
do map.consume |name, value| {
242232
match self.local_vars.find_mut(&name) {
243233
Some(v) => { v.data = copy *value; }

0 commit comments

Comments
 (0)