about summary refs log tree commit diff
path: root/src/rt
diff options
context:
space:
mode:
Diffstat (limited to 'src/rt')
-rw-r--r--src/rt/rust_builtin.cpp14
-rw-r--r--src/rt/rust_env.cpp2
-rw-r--r--src/rt/rust_env.h1
-rw-r--r--src/rt/rust_task.cpp11
-rw-r--r--src/rt/rust_task.h5
-rw-r--r--src/rt/rustrt.def.in2
6 files changed, 35 insertions, 0 deletions
diff --git a/src/rt/rust_builtin.cpp b/src/rt/rust_builtin.cpp
index 8b7b89680fc..a491379153e 100644
--- a/src/rt/rust_builtin.cpp
+++ b/src/rt/rust_builtin.cpp
@@ -683,6 +683,20 @@ rust_task_local_data_atexit(rust_task *task, void (*cleanup_fn)(void *data)) {
     task->task_local_data_cleanup = cleanup_fn;
 }
 
+// set/get/atexit task_borrow_list can run on the rust stack for speed.
+extern "C" void *
+rust_take_task_borrow_list(rust_task *task) {
+    void *r = task->borrow_list;
+    task->borrow_list = NULL;
+    return r;
+}
+extern "C" void
+rust_set_task_borrow_list(rust_task *task, void *data) {
+    assert(task->borrow_list == NULL);
+    assert(data != NULL);
+    task->borrow_list = data;
+}
+
 extern "C" void
 task_clear_event_reject(rust_task *task) {
     task->clear_event_reject();
diff --git a/src/rt/rust_env.cpp b/src/rt/rust_env.cpp
index 041b4efac52..360d6114928 100644
--- a/src/rt/rust_env.cpp
+++ b/src/rt/rust_env.cpp
@@ -24,6 +24,7 @@
 #define RUST_SEED "RUST_SEED"
 #define RUST_POISON_ON_FREE "RUST_POISON_ON_FREE"
 #define RUST_DEBUG_MEM "RUST_DEBUG_MEM"
+#define RUST_DEBUG_BORROW "RUST_DEBUG_BORROW"
 
 #if defined(__WIN32__)
 static int
@@ -130,6 +131,7 @@ load_env(int argc, char **argv) {
     env->argc = argc;
     env->argv = argv;
     env->debug_mem = getenv(RUST_DEBUG_MEM) != NULL;
+    env->debug_borrow = getenv(RUST_DEBUG_BORROW) != NULL;
     return env;
 }
 
diff --git a/src/rt/rust_env.h b/src/rt/rust_env.h
index df27f7674f2..b897f0c09a9 100644
--- a/src/rt/rust_env.h
+++ b/src/rt/rust_env.h
@@ -28,6 +28,7 @@ struct rust_env {
     int argc;
     char **argv;
     rust_bool debug_mem;
+    rust_bool debug_borrow;
 };
 
 rust_env* load_env(int argc, char **argv);
diff --git a/src/rt/rust_task.cpp b/src/rt/rust_task.cpp
index 7e3c91f6211..23e70535768 100644
--- a/src/rt/rust_task.cpp
+++ b/src/rt/rust_task.cpp
@@ -42,6 +42,7 @@ rust_task::rust_task(rust_sched_loop *sched_loop, rust_task_state state,
     total_stack_sz(0),
     task_local_data(NULL),
     task_local_data_cleanup(NULL),
+    borrow_list(NULL),
     state(state),
     cond(NULL),
     cond_name("none"),
@@ -75,6 +76,16 @@ rust_task::delete_this()
     assert(ref_count == 0); // ||
     //   (ref_count == 1 && this == sched->root_task));
 
+    if (borrow_list) {
+        // NOTE should free borrow_list from within rust code!
+        // If there is a pointer in there, it is a ~[BorrowRecord] pointer,
+        // which are currently allocated with LIBC malloc/free. But this is
+        // not really the right way to do this, we should be freeing this
+        // pointer from Rust code.
+        free(borrow_list);
+        borrow_list = NULL;
+    }
+
     sched_loop->release_task(this);
 }
 
diff --git a/src/rt/rust_task.h b/src/rt/rust_task.h
index fd4e8451b64..b76a177e1c8 100644
--- a/src/rt/rust_task.h
+++ b/src/rt/rust_task.h
@@ -245,6 +245,11 @@ rust_task : public kernel_owned<rust_task>
     void *task_local_data;
     void (*task_local_data_cleanup)(void *data);
 
+    // Contains a ~[BorrowRecord] pointer, or NULL.
+    //
+    // Used by borrow management code in libcore/unstable/lang.rs.
+    void *borrow_list;
+
 private:
 
     // Protects state, cond, cond_name
diff --git a/src/rt/rustrt.def.in b/src/rt/rustrt.def.in
index 3ca05b94711..1c3f6370ded 100644
--- a/src/rt/rustrt.def.in
+++ b/src/rt/rustrt.def.in
@@ -233,3 +233,5 @@ rust_boxed_region_malloc
 rust_boxed_region_free
 rust_try
 rust_begin_unwind
+rust_take_task_borrow_list
+rust_set_task_borrow_list