Prefer to use Fiber#transfer
in scheduler implementation. (#10479)
This commit is contained in:
parent
ed4d03ea41
commit
bdb1fc1e5b
@ -27,7 +27,9 @@ class Scheduler
|
|||||||
Warning[:experimental] = experimental
|
Warning[:experimental] = experimental
|
||||||
end
|
end
|
||||||
|
|
||||||
def initialize
|
def initialize(fiber = Fiber.current)
|
||||||
|
@fiber = fiber
|
||||||
|
|
||||||
@readable = {}
|
@readable = {}
|
||||||
@writable = {}
|
@writable = {}
|
||||||
@waiting = {}
|
@waiting = {}
|
||||||
@ -45,6 +47,10 @@ class Scheduler
|
|||||||
attr :writable
|
attr :writable
|
||||||
attr :waiting
|
attr :waiting
|
||||||
|
|
||||||
|
def transfer
|
||||||
|
@fiber.transfer
|
||||||
|
end
|
||||||
|
|
||||||
def next_timeout
|
def next_timeout
|
||||||
_fiber, timeout = @waiting.min_by{|key, value| value}
|
_fiber, timeout = @waiting.min_by{|key, value| value}
|
||||||
|
|
||||||
@ -88,7 +94,7 @@ class Scheduler
|
|||||||
end
|
end
|
||||||
|
|
||||||
selected.each do |fiber, events|
|
selected.each do |fiber, events|
|
||||||
fiber.resume(events)
|
fiber.transfer(events)
|
||||||
end
|
end
|
||||||
|
|
||||||
if @waiting.any?
|
if @waiting.any?
|
||||||
@ -98,7 +104,7 @@ class Scheduler
|
|||||||
waiting.each do |fiber, timeout|
|
waiting.each do |fiber, timeout|
|
||||||
if fiber.alive?
|
if fiber.alive?
|
||||||
if timeout <= time
|
if timeout <= time
|
||||||
fiber.resume
|
fiber.transfer
|
||||||
else
|
else
|
||||||
@waiting[fiber] = timeout
|
@waiting[fiber] = timeout
|
||||||
end
|
end
|
||||||
@ -114,7 +120,7 @@ class Scheduler
|
|||||||
end
|
end
|
||||||
|
|
||||||
ready.each do |fiber|
|
ready.each do |fiber|
|
||||||
fiber.resume
|
fiber.transfer
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@ -217,7 +223,7 @@ class Scheduler
|
|||||||
@waiting[fiber] = current_time + duration
|
@waiting[fiber] = current_time + duration
|
||||||
end
|
end
|
||||||
|
|
||||||
Fiber.yield
|
@fiber.transfer
|
||||||
ensure
|
ensure
|
||||||
@waiting.delete(fiber) if duration
|
@waiting.delete(fiber) if duration
|
||||||
@readable.delete(io) if readable
|
@readable.delete(io) if readable
|
||||||
@ -254,7 +260,7 @@ class Scheduler
|
|||||||
if timeout
|
if timeout
|
||||||
@waiting[fiber] = current_time + timeout
|
@waiting[fiber] = current_time + timeout
|
||||||
begin
|
begin
|
||||||
Fiber.yield
|
@fiber.transfer
|
||||||
ensure
|
ensure
|
||||||
# Remove from @waiting in the case #unblock was called before the timeout expired:
|
# Remove from @waiting in the case #unblock was called before the timeout expired:
|
||||||
@waiting.delete(fiber)
|
@waiting.delete(fiber)
|
||||||
@ -262,7 +268,7 @@ class Scheduler
|
|||||||
else
|
else
|
||||||
@blocking[fiber] = true
|
@blocking[fiber] = true
|
||||||
begin
|
begin
|
||||||
Fiber.yield
|
@fiber.transfer
|
||||||
ensure
|
ensure
|
||||||
@blocking.delete(fiber)
|
@blocking.delete(fiber)
|
||||||
end
|
end
|
||||||
@ -290,7 +296,7 @@ class Scheduler
|
|||||||
def fiber(&block)
|
def fiber(&block)
|
||||||
fiber = Fiber.new(blocking: false, &block)
|
fiber = Fiber.new(blocking: false, &block)
|
||||||
|
|
||||||
fiber.resume
|
fiber.transfer
|
||||||
|
|
||||||
return fiber
|
return fiber
|
||||||
end
|
end
|
||||||
|
@ -207,7 +207,7 @@ class TestFiberMutex < Test::Unit::TestCase
|
|||||||
Fiber.schedule do
|
Fiber.schedule do
|
||||||
mutex.synchronize do
|
mutex.synchronize do
|
||||||
puts 'in synchronize'
|
puts 'in synchronize'
|
||||||
Fiber.yield
|
scheduler.transfer
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user