Project

General

Profile

Feature #11498 ยป loop-result.patch

knu (Akinori MUSHA), 09/01/2015 09:09 AM

View differences:

ChangeLog
1
Tue Sep  1 14:49:27 2015  Akinori MUSHA  <knu@iDaemons.org>
2

  
3
	* vm_eval.c (rb_f_loop): When a loop is stopped by a StopIteration
4
	  exception, return what the enumerator has returned instead of
5
	  nil.
6

  
1 7
Mon Aug 31 17:04:45 2015  Koichi Sasada  <ko1@atdot.net>
2 8

  
3 9
	* class.c (move_refined_method): should insert a write barrier
NEWS
44 44
    this parameter is bitwise-ORed to oflags generated by normal mode argument.
45 45
    [Feature #11253]
46 46

  
47
* Kernel
48

  
49
  * Kernel#loop, when stopped by a StopIteration exception, returns
50
    what the enumerator has returned instead of nil.
51

  
47 52
* Module
48 53
  * Module#deprecate_constant [Feature #11398]
49 54

  
test/ruby/test_enumerator.rb
46 46
    }
47 47
  end
48 48

  
49
  def test_loop_return_value
50
    assert_equal nil, loop { break }
51
    assert_equal 42,  loop { break 42 }
52

  
53
    e = Enumerator.new { |y| y << 1; y << 2; :stopped }
54
    assert_equal :stopped, loop { e.next while true }
55
  end
56

  
49 57
  def test_nested_iteration
50 58
    def (o = Object.new).each
51 59
      yield :ok1
vm_eval.c
24 24
static int vm_collect_local_variables_in_heap(rb_thread_t *th, const VALUE *dfp, const struct local_var_list *vars);
25 25

  
26 26
static VALUE rb_eUncaughtThrow;
27
static ID id_tag, id_value;
27
static ID id_result, id_tag, id_value;
28 28
#define id_mesg idMesg
29 29

  
30 30
/* vm_backtrace.c */
......
1067 1067
}
1068 1068

  
1069 1069
static VALUE
1070
loop_stop(VALUE dummy, VALUE exc)
1071
{
1072
    return rb_attr_get(exc, id_result);
1073
}
1074

  
1075
static VALUE
1070 1076
rb_f_loop_size(VALUE self, VALUE args, VALUE eobj)
1071 1077
{
1072 1078
    return DBL2NUM(INFINITY);
......
1095 1101
rb_f_loop(VALUE self)
1096 1102
{
1097 1103
    RETURN_SIZED_ENUMERATOR(self, 0, 0, rb_f_loop_size);
1098
    rb_rescue2(loop_i, (VALUE)0, 0, 0, rb_eStopIteration, (VALUE)0);
1099
    return Qnil;		/* dummy */
1104
    return rb_rescue2(loop_i, (VALUE)0, loop_stop, (VALUE)0, rb_eStopIteration, (VALUE)0);
1100 1105
}
1101 1106

  
1102 1107
#if VMDEBUG
......
2172 2177
    rb_define_method(rb_eUncaughtThrow, "value", uncaught_throw_value, 0);
2173 2178
    rb_define_method(rb_eUncaughtThrow, "to_s", uncaught_throw_to_s, 0);
2174 2179

  
2180
    id_result = rb_intern_const("result");
2175 2181
    id_tag = rb_intern_const("tag");
2176 2182
    id_value = rb_intern_const("value");
2177 2183
}