Commit 19c4bf6f authored by take_cheeze's avatar take_cheeze

revert MRB_FIBER_RESUMED as MRB_FIBER_RESUMING to fix recurive resume

parent 792c1add
...@@ -70,6 +70,7 @@ typedef struct { ...@@ -70,6 +70,7 @@ typedef struct {
enum mrb_fiber_state { enum mrb_fiber_state {
MRB_FIBER_CREATED = 0, MRB_FIBER_CREATED = 0,
MRB_FIBER_RUNNING, MRB_FIBER_RUNNING,
MRB_FIBER_RESUMING,
MRB_FIBER_SUSPENDED, MRB_FIBER_SUSPENDED,
MRB_FIBER_TERMINATED, MRB_FIBER_TERMINATED,
}; };
......
...@@ -164,13 +164,14 @@ fiber_resume(mrb_state *mrb, mrb_value self) ...@@ -164,13 +164,14 @@ fiber_resume(mrb_state *mrb, mrb_value self)
mrb_raise(mrb, E_ARGUMENT_ERROR, "can't cross C function boundary"); mrb_raise(mrb, E_ARGUMENT_ERROR, "can't cross C function boundary");
} }
} }
if (c->status == MRB_FIBER_RUNNING || (mrb->c->prev && mrb->c->prev != mrb->root_c)) { if (c->status == MRB_FIBER_RUNNING || c->status == MRB_FIBER_RESUMING) {
mrb_raise(mrb, E_RUNTIME_ERROR, "double resume"); mrb_raise(mrb, E_RUNTIME_ERROR, "double resume");
} }
if (c->status == MRB_FIBER_TERMINATED) { if (c->status == MRB_FIBER_TERMINATED) {
mrb_raise(mrb, E_RUNTIME_ERROR, "resuming dead fiber"); mrb_raise(mrb, E_RUNTIME_ERROR, "resuming dead fiber");
} }
mrb_get_args(mrb, "*", &a, &len); mrb_get_args(mrb, "*", &a, &len);
mrb->c->status = MRB_FIBER_RESUMING;
if (c->status == MRB_FIBER_CREATED) { if (c->status == MRB_FIBER_CREATED) {
mrb_value *b = c->stack+1; mrb_value *b = c->stack+1;
mrb_value *e = b + len; mrb_value *e = b + len;
...@@ -183,7 +184,6 @@ fiber_resume(mrb_state *mrb, mrb_value self) ...@@ -183,7 +184,6 @@ fiber_resume(mrb_state *mrb, mrb_value self)
if (c->prev->fib) if (c->prev->fib)
mrb_field_write_barrier(mrb, (struct RBasic*)c->fib, (struct RBasic*)c->prev->fib); mrb_field_write_barrier(mrb, (struct RBasic*)c->fib, (struct RBasic*)c->prev->fib);
mrb_write_barrier(mrb, (struct RBasic*)c->fib); mrb_write_barrier(mrb, (struct RBasic*)c->fib);
mrb->c->status = MRB_FIBER_SUSPENDED;
c->status = MRB_FIBER_RUNNING; c->status = MRB_FIBER_RUNNING;
mrb->c = c; mrb->c = c;
...@@ -195,7 +195,6 @@ fiber_resume(mrb_state *mrb, mrb_value self) ...@@ -195,7 +195,6 @@ fiber_resume(mrb_state *mrb, mrb_value self)
if (c->prev->fib) if (c->prev->fib)
mrb_field_write_barrier(mrb, (struct RBasic*)c->fib, (struct RBasic*)c->prev->fib); mrb_field_write_barrier(mrb, (struct RBasic*)c->fib, (struct RBasic*)c->prev->fib);
mrb_write_barrier(mrb, (struct RBasic*)c->fib); mrb_write_barrier(mrb, (struct RBasic*)c->fib);
mrb->c->status = MRB_FIBER_SUSPENDED;
c->status = MRB_FIBER_RUNNING; c->status = MRB_FIBER_RUNNING;
mrb->c = c; mrb->c = c;
return fiber_result(mrb, a, len); return fiber_result(mrb, a, len);
......
...@@ -96,8 +96,12 @@ assert('Recursive resume of Fiber') do ...@@ -96,8 +96,12 @@ assert('Recursive resume of Fiber') do
f1.resume f1.resume
Fiber.yield 0 Fiber.yield 0
} }
assert_equal 0, f2.resume f3 = Fiber.new {
f2.resume
}
assert_equal 0, f3.resume
f2.resume f2.resume
assert_false f1.alive? assert_false f1.alive?
assert_false f2.alive? assert_false f2.alive?
assert_false f3.alive?
end end
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment