Add alternative optional hook for scheduler_close to allow public usage of close.

This commit is contained in:
Samuel Williams 2021-07-19 10:14:51 +12:00
parent 4730a1e0ec
commit cb8434563d
Notes: git 2021-09-20 19:08:17 +09:00
2 changed files with 24 additions and 6 deletions

View File

@ -13,6 +13,7 @@
#include "ruby/io.h" #include "ruby/io.h"
static ID id_close; static ID id_close;
static ID id_scheduler_close;
static ID id_block; static ID id_block;
static ID id_unblock; static ID id_unblock;
@ -31,6 +32,7 @@ void
Init_Fiber_Scheduler(void) Init_Fiber_Scheduler(void)
{ {
id_close = rb_intern_const("close"); id_close = rb_intern_const("close");
id_scheduler_close = rb_intern_const("scheduler_close");
id_block = rb_intern_const("block"); id_block = rb_intern_const("block");
id_unblock = rb_intern_const("unblock"); id_unblock = rb_intern_const("unblock");
@ -122,9 +124,13 @@ VALUE rb_fiber_scheduler_current_for_thread(VALUE thread)
VALUE VALUE
rb_fiber_scheduler_close(VALUE scheduler) rb_fiber_scheduler_close(VALUE scheduler)
{ {
if (rb_respond_to(scheduler, id_close)) { VALUE result;
return rb_funcall(scheduler, id_close, 0);
} result = rb_check_funcall(scheduler, id_scheduler_close, 0, NULL);
if (result != Qundef) return result;
result = rb_check_funcall(scheduler, id_close, 0, NULL);
if (result != Qundef) return result;
return Qnil; return Qnil;
} }

View File

@ -107,10 +107,22 @@ class Scheduler
end end
end end
def close def scheduler_close
close(true)
end
def close(internal = false)
# $stderr.puts [__method__, Fiber.current].inspect # $stderr.puts [__method__, Fiber.current].inspect
raise "Scheduler already closed!" if @closed unless internal
if Fiber.scheduler == self
return Fiber.set_scheduler(nil)
end
end
if @closed
raise "Scheduler already closed!"
end
self.run self.run
ensure ensure
@ -119,7 +131,7 @@ class Scheduler
@urgent = nil @urgent = nil
end end
@closed = true @closed ||= true
# We freeze to detect any unintended modifications after the scheduler is closed: # We freeze to detect any unintended modifications after the scheduler is closed:
self.freeze self.freeze