ruby-core@ruby-lang.org archive (unofficial mirror)
 help / color / mirror / Atom feed
* [ruby-core:73588] [Ruby trunk - Bug #12036] [Open] Enumerator's automatic rewind behavior
       [not found] <redmine.issue-12036.20160129213058@ruby-lang.org>
@ 2016-01-29 21:30 ` tad.hosford
  2017-09-06  4:29 ` [ruby-core:82665] [Ruby trunk Bug#12036] " xkernigh
  1 sibling, 0 replies; 2+ messages in thread
From: tad.hosford @ 2016-01-29 21:30 UTC (permalink / raw
  To: ruby-core

Issue #12036 has been reported by Ryan Hosford.

----------------------------------------
Bug #12036: Enumerator's automatic rewind behavior
https://bugs.ruby-lang.org/issues/12036

* Author: Ryan Hosford
* Status: Open
* Priority: Normal
* Assignee: 
* ruby -v: 
* Backport: 2.0.0: UNKNOWN, 2.1: UNKNOWN, 2.2: UNKNOWN, 2.3: UNKNOWN
----------------------------------------
When enumerating an enumerator, the enumerator automatically rewinds when #next raises an error. The concern here is that someone may need to handle that error and continue processing the rest of the enumerator.

12:22 < Ox0dea> I think tjohnson found where the StopIteration was being raised?
12:23 < tjohnson> A friend in #projecthydra pointed me here:  https://github.com/ruby/ruby/blob/trunk/enumerator.c#L655-L660
12:24 < tjohnson> seems quite deliberate. compare: https://github.com/ruby/ruby/blob/trunk/enumerator.c#L925-L930
12:25 < Ox0dea> Yeah, Line 651 in there is the one birthing the new Fiber, and since dead ones don't maintain context, the surrounding Enumerator can't pick up where it left off.
**12:26 < Ox0dea> It's almost certainly intentional, and most likely even The Right Thing, but "make easy things easy and hard things *possible*".**

tjohnson first demonstrated the behavior in a gist: https://gist.github.com/no-reply/4b38f26b3fe32ad266a7#gistcomment-1683794
lucasb also produced a snippet that clearly demonstrates the behavior: https://eval.in/509874


Thanks:
0x0dea, lucasb, tjohnson, rthbound



-- 
https://bugs.ruby-lang.org/

^ permalink raw reply	[flat|nested] 2+ messages in thread

* [ruby-core:82665] [Ruby trunk Bug#12036] Enumerator's automatic rewind behavior
       [not found] <redmine.issue-12036.20160129213058@ruby-lang.org>
  2016-01-29 21:30 ` [ruby-core:73588] [Ruby trunk - Bug #12036] [Open] Enumerator's automatic rewind behavior tad.hosford
@ 2017-09-06  4:29 ` xkernigh
  1 sibling, 0 replies; 2+ messages in thread
From: xkernigh @ 2017-09-06  4:29 UTC (permalink / raw
  To: ruby-core

Issue #12036 has been updated by kernigh (George Koehler).


I don't want Ruby to change this behavior. Enumerable#next can't continue the iteration if it raises an exception. That's why it has the automatic rewind behavior.

Here's a quick example. In this script, we handle the oops and expect the last `e.next` to return 44, but there is automatic rewind so it returns 11.

```ruby
def peach
  yield 11
  yield 22
  fail 'oops'
  yield 44
end

e = enum_for(:peach)
puts e.next              #=> 11
puts e.next              #=> 22
(e.next rescue puts $!)  #=> oops
puts e.next              #=> 11
```

Now we want to change the behavior of Enumerable#next so it would return 44. This seems impossible, because #peach always raises an error and never reaches `yield 44`. To make this change, we would need to modify Ruby to divert some errors between fibers. When the fiber running #peach tries to raise an error, Ruby would switch to the fiber running Enumerable#next before raising the error. Later, if the program switches back to the fiber of #peach, *then #peach would continue as if it had never raised an error.* With this change, the caller of #next can rescue the error, and #peach can reach `yield 44`.

In our modified Ruby, Enumerable#next would divert errors that should never be diverted. The next script might crash our modified Ruby.

```ruby
def teach
  "str" + 2
end

e = enum_for(:teach)
(e.next rescue puts $!)
#=> no implicit conversion of Integer into String
e.next
#=> crash Ruby???
```

We rescue a TypeError from String#+, then tell Ruby to continue the iteration. Our modified Ruby wouldn't have automatic rewind, so the fiber running #teach would continue the execution of String#+ as if it never raised TypeError. Then the C code implementing String#+ might use 2 as a String and crash Ruby! This is why I want Ruby to keep automatic rewind.

----------------------------------------
Bug #12036: Enumerator's automatic rewind behavior
https://bugs.ruby-lang.org/issues/12036#change-66494

* Author: slash_nick (Ryan Hosford)
* Status: Open
* Priority: Normal
* Assignee: 
* Target version: 
* ruby -v: 
* Backport: 2.0.0: UNKNOWN, 2.1: UNKNOWN, 2.2: UNKNOWN, 2.3: UNKNOWN
----------------------------------------
When enumerating an enumerator, the enumerator automatically rewinds when #next raises an error. The concern here is that someone may need to handle that error and continue processing the rest of the enumerator.

12:22 < Ox0dea> I think tjohnson found where the StopIteration was being raised?
12:23 < tjohnson> A friend in #projecthydra pointed me here:  https://github.com/ruby/ruby/blob/trunk/enumerator.c#L655-L660
12:24 < tjohnson> seems quite deliberate. compare: https://github.com/ruby/ruby/blob/trunk/enumerator.c#L925-L930
12:25 < Ox0dea> Yeah, Line 651 in there is the one birthing the new Fiber, and since dead ones don't maintain context, the surrounding Enumerator can't pick up where it left off.
**12:26 < Ox0dea> It's almost certainly intentional, and most likely even The Right Thing, but "make easy things easy and hard things *possible*".**

tjohnson first demonstrated the behavior in a gist: https://gist.github.com/no-reply/4b38f26b3fe32ad266a7#gistcomment-1683794
lucasb also produced a snippet that clearly demonstrates the behavior: https://eval.in/509874


Thanks:
0x0dea, lucasb, tjohnson, rthbound



-- 
https://bugs.ruby-lang.org/

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2017-09-06  4:29 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
     [not found] <redmine.issue-12036.20160129213058@ruby-lang.org>
2016-01-29 21:30 ` [ruby-core:73588] [Ruby trunk - Bug #12036] [Open] Enumerator's automatic rewind behavior tad.hosford
2017-09-06  4:29 ` [ruby-core:82665] [Ruby trunk Bug#12036] " xkernigh

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).