about summary refs log tree commit diff
path: root/src/rt
diff options
context:
space:
mode:
authorBrian Anderson <banderson@mozilla.com>2012-02-22 23:50:27 -0800
committerBrian Anderson <banderson@mozilla.com>2012-02-22 23:50:47 -0800
commitb5c7997ef588916e566c18ba91608454bc4ffaaf (patch)
tree00e12238b49663ac9d9a800120572852f6ae2499 /src/rt
parentc16bfbe0c365b6d3f0c274a53bc1374822766e6b (diff)
downloadrust-b5c7997ef588916e566c18ba91608454bc4ffaaf.tar.gz
rust-b5c7997ef588916e566c18ba91608454bc4ffaaf.zip
rt: Switch to the C stack in reset_stack_limit
Diffstat (limited to 'src/rt')
-rw-r--r--src/rt/rust_task.cpp27
-rw-r--r--src/rt/rust_task.h2
2 files changed, 24 insertions, 5 deletions
diff --git a/src/rt/rust_task.cpp b/src/rt/rust_task.cpp
index f8fd01d4a49..f2bb15796f2 100644
--- a/src/rt/rust_task.cpp
+++ b/src/rt/rust_task.cpp
@@ -687,6 +687,23 @@ sp_in_stk_seg(uintptr_t sp, stk_seg *stk) {
     return (uintptr_t)stk->data <= sp && sp <= stk->end;
 }
 
+struct reset_args {
+    rust_task *task;
+    uintptr_t sp;
+};
+
+void
+reset_stack_limit_on_c_stack(reset_args *args) {
+    rust_task *task = args->task;
+    uintptr_t sp = args->sp;
+    while (!sp_in_stk_seg(sp, task->stk)) {
+        task->del_stack();
+        A(task->thread, task->stk != NULL,
+          "Failed to find the current stack");
+    }
+    task->record_stack_limit();
+}
+
 /*
 Called by landing pads during unwinding to figure out which
 stack segment we are currently running on, delete the others,
@@ -695,12 +712,12 @@ through __morestack).
  */
 void
 rust_task::reset_stack_limit() {
+    I(thread, on_rust_stack());
     uintptr_t sp = get_sp();
-    while (!sp_in_stk_seg(sp, stk)) {
-        del_stack();
-        A(thread, stk != NULL, "Failed to find the current stack");
-    }
-    record_stack_limit();
+    // Have to do the rest on the C stack because it involves
+    // freeing stack segments, logging, etc.
+    reset_args ra = {this, sp};
+    call_on_c_stack(&ra, (void*)reset_stack_limit_on_c_stack);
 }
 
 void
diff --git a/src/rt/rust_task.h b/src/rt/rust_task.h
index fe1b94d6ea5..b1610f57582 100644
--- a/src/rt/rust_task.h
+++ b/src/rt/rust_task.h
@@ -39,6 +39,7 @@ typedef unsigned long task_result;
 
 struct spawn_args;
 struct cleanup_args;
+struct reset_args;
 
 // std::lib::task::task_notification
 //
@@ -131,6 +132,7 @@ private:
 
     friend void task_start_wrapper(spawn_args *a);
     friend void cleanup_task(cleanup_args *a);
+    friend void reset_stack_limit_on_c_stack(reset_args *a);
 
 public: