Bug #20082
openKilling fibers across threads: unexpected exception
Description
For providing the example in a changelog, I tried to imitate killing fibers belonging to other threads.
Documentation claims
Raises FiberError if called on a fiber belonging to another thread.
So, I created this artificial example to check how it works:
fibers = []
Thread.new {
f = Fiber.new { (1..).each { sleep(0.1) } }
fibers << f
f.resume
}
sleep(0.1) # to make sure the thread has started
fibers.last.kill
The example indeed fails with FiberError
, but the error message is confusing:
in `kill': attempt to resume a resumed fiber (double resume) (FiberError)
Is this an expected message for such case? Or am I misunderstanding something?
Updated by zverok (Victor Shepelev) 8 months ago
UPD: OTOH, without resuming, the code doesn't see any problem at all (despite the claim about killing other thread's fibers):
fibers = []
Thread.new {
f = Fiber.new { (1..).each { sleep(0.1) } }
fibers << f
}
sleep(0.1) # to make sure the thread have started
p fibers.last.kill
#=> #<Fiber:0x00007f73f682c078 examples/fiber_kill.rb:7 (terminated)>
Updated by rubyFeedback (robert heiler) 8 months ago
The error message is indeed somewhat peculiar:
"attempt to resume a resumed fiber ( double resume )"
I am not sure what "double resume" means here. But, even aside
from this, I could not even try to want to explain what "to
resume a resumed fiber" really means. Perhaps something else
was meant here? Or it was meant to convey that the code tried
to resume an already-resumed fiber. Either way it is indeed
peculiar.
I'd even be radical and suggest to get rid of fibers and instead
put everything under Thread, but I guess that is not possible
for various reasons. To me Threads seem easier to understand
than Fibers though.
Updated by ioquatix (Samuel Williams) 8 months ago
Raises FiberError if called on a fiber belonging to another thread.
I agree the error is a little confusing, but the reality is it's probably okay.
"in `kill': attempt to resume a resumed fiber (double resume) (FiberError)"
You are literally reaching across into a fiber which is currently resumed and executing sleep. This is a text book definition of a double resume.
To get the error message I imagine you are after:
fibers = []
Thread.new {
f = Fiber.new { Fiber.yield }
f.resume
fibers << f
}.join
fibers.last.kill
without resuming, the code doesn't see any problem at all (despite the claim about killing other thread's fibers):
A fiber is lazily constructed according to the first thread it is resumed on. So, this behaviour looks okay to me.
Updated by hsbt (Hiroshi SHIBATA) 5 months ago
- Status changed from Open to Assigned