diff --git a/src/librustc/middle/astencode.rs b/src/librustc/middle/astencode.rs
index eefd99824e6..32f4c9858f7 100644
--- a/src/librustc/middle/astencode.rs
+++ b/src/librustc/middle/astencode.rs
@@ -946,7 +946,8 @@ fn encode_side_tables_for_id(ecx: &e::EncodeContext,
     }
 
     {
-        let r = tcx.freevars.find(&id);
+        let freevars = tcx.freevars.borrow();
+        let r = freevars.get().find(&id);
         for &fv in r.iter() {
             ebml_w.tag(c::tag_table_freevars, |ebml_w| {
                 ebml_w.id(id);
@@ -1256,7 +1257,8 @@ fn decode_side_tables(xcx: @ExtendedDecodeContext,
                         let fv_info = @val_dsr.read_to_vec(|val_dsr| {
                             @val_dsr.read_freevar_entry(xcx)
                         });
-                        dcx.tcx.freevars.insert(id, fv_info);
+                        let mut freevars = dcx.tcx.freevars.borrow_mut();
+                        freevars.get().insert(id, fv_info);
                     }
                     c::tag_table_tcache => {
                         let tpbt = val_dsr.read_ty_param_bounds_and_ty(xcx);
diff --git a/src/librustc/middle/freevars.rs b/src/librustc/middle/freevars.rs
index 2b1154480c8..35ec5d638b7 100644
--- a/src/librustc/middle/freevars.rs
+++ b/src/librustc/middle/freevars.rs
@@ -30,7 +30,7 @@ pub struct freevar_entry {
     span: Span     //< First span where it is accessed (there can be multiple)
 }
 pub type freevar_info = @~[@freevar_entry];
-pub type freevar_map = @mut HashMap<ast::NodeId, freevar_info>;
+pub type freevar_map = HashMap<ast::NodeId, freevar_info>;
 
 struct CollectFreevarsVisitor {
     seen: HashMap<ast::NodeId, ()>,
@@ -128,21 +128,24 @@ impl Visitor<()> for AnnotateFreevarsVisitor {
 // one pass. This could be improved upon if it turns out to matter.
 pub fn annotate_freevars(def_map: resolve::DefMap, crate: &ast::Crate) ->
    freevar_map {
-    let freevars = @mut HashMap::new();
-
     let mut visitor = AnnotateFreevarsVisitor {
         def_map: def_map,
-        freevars: freevars,
+        freevars: HashMap::new(),
     };
     visit::walk_crate(&mut visitor, crate, ());
 
-    return freevars;
+    let AnnotateFreevarsVisitor {
+        freevars,
+        ..
+    } = visitor;
+    freevars
 }
 
 pub fn get_freevars(tcx: ty::ctxt, fid: ast::NodeId) -> freevar_info {
-    match tcx.freevars.find(&fid) {
-      None => fail!("get_freevars: {} has no freevars", fid),
-      Some(&d) => return d
+    let freevars = tcx.freevars.borrow();
+    match freevars.get().find(&fid) {
+        None => fail!("get_freevars: {} has no freevars", fid),
+        Some(&d) => return d
     }
 }
 
diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs
index 2f13443e071..339eb12bd06 100644
--- a/src/librustc/middle/ty.rs
+++ b/src/librustc/middle/ty.rs
@@ -303,7 +303,7 @@ struct ctxt_ {
     /// also to expr/stmt/local/arg/etc
     items: ast_map::map,
     intrinsic_defs: RefCell<HashMap<ast::DefId, t>>,
-    freevars: freevars::freevar_map,
+    freevars: RefCell<freevars::freevar_map>,
     tcache: type_cache,
     rcache: creader_cache,
     short_names_cache: RefCell<HashMap<t, @str>>,
@@ -981,7 +981,7 @@ pub fn mk_ctxt(s: session::Session,
         trait_defs: RefCell::new(HashMap::new()),
         items: amap,
         intrinsic_defs: RefCell::new(HashMap::new()),
-        freevars: freevars,
+        freevars: RefCell::new(freevars),
         tcache: RefCell::new(HashMap::new()),
         rcache: RefCell::new(HashMap::new()),
         short_names_cache: RefCell::new(HashMap::new()),