Project

General

Profile

Actions

Bug #20082

open

Killing fibers across threads: unexpected exception

Added by zverok (Victor Shepelev) 2 months ago. Updated 2 months ago.

Status:
Open
Target version:
-
[ruby-core:115881]

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) 2 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) 2 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) 2 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.

Actions

Also available in: Atom PDF

Like0
Like0Like0Like0