[前][次][番号順一覧][スレッド一覧]

ruby-changes:29307

From: ktsj <ko1@a...>
Date: Mon, 17 Jun 2013 21:39:07 +0900 (JST)
Subject: [ruby-changes:29307] ktsj:r41359 (trunk): * include/ruby/intern.h, proc.c (rb_method_call_with_block):

ktsj	2013-06-17 21:38:52 +0900 (Mon, 17 Jun 2013)

  New Revision: 41359

  http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=41359

  Log:
    * include/ruby/intern.h, proc.c (rb_method_call_with_block):
      new function to invoke a Method object with a block passed
      as an argument.
    
    * proc.c (bmcall): use the above function to avoid a block sharing.
      [ruby-core:54626] [Bug #8341]
    
    * test/ruby/test_proc.rb (TestProc#test_block_persist_between_calls):
      run related tests.

  Modified files:
    trunk/ChangeLog
    trunk/include/ruby/intern.h
    trunk/proc.c
    trunk/test/ruby/test_proc.rb

Index: include/ruby/intern.h
===================================================================
--- include/ruby/intern.h	(revision 41358)
+++ include/ruby/intern.h	(revision 41359)
@@ -380,6 +380,7 @@ VALUE rb_binding_new(void); https://github.com/ruby/ruby/blob/trunk/include/ruby/intern.h#L380
 VALUE rb_obj_method(VALUE, VALUE);
 VALUE rb_obj_is_method(VALUE);
 VALUE rb_method_call(int, VALUE*, VALUE);
+VALUE rb_method_call_with_block(int, VALUE *, VALUE, VALUE);
 int rb_mod_method_arity(VALUE, ID);
 int rb_obj_method_arity(VALUE, ID);
 VALUE rb_protect(VALUE (*)(VALUE), VALUE, int*);
Index: ChangeLog
===================================================================
--- ChangeLog	(revision 41358)
+++ ChangeLog	(revision 41359)
@@ -1,3 +1,15 @@ https://github.com/ruby/ruby/blob/trunk/ChangeLog#L1
+Mon Jun 17 21:33:27 2013  Kazuki Tsujimoto  <kazuki@c...>
+
+	* include/ruby/intern.h, proc.c (rb_method_call_with_block):
+	  new function to invoke a Method object with a block passed
+	  as an argument.
+
+	* proc.c (bmcall): use the above function to avoid a block sharing.
+	  [ruby-core:54626] [Bug #8341]
+
+	* test/ruby/test_proc.rb (TestProc#test_block_persist_between_calls):
+	  run related tests.
+
 Mon Jun 17 20:53:21 2013  Tanaka Akira  <akr@f...>
 
 	* loadpath.c (RUBY_REVISION): Defined to suppress revision.h
Index: proc.c
===================================================================
--- proc.c	(revision 41358)
+++ proc.c	(revision 41359)
@@ -28,7 +28,7 @@ VALUE rb_cMethod; https://github.com/ruby/ruby/blob/trunk/proc.c#L28
 VALUE rb_cBinding;
 VALUE rb_cProc;
 
-static VALUE bmcall(VALUE, VALUE);
+static VALUE bmcall(VALUE, VALUE, int, VALUE *, VALUE);
 static int method_arity(VALUE);
 static int method_min_max_arity(VALUE, int *max);
 #define attached id__attached__
@@ -1593,6 +1593,13 @@ method_clone(VALUE self) https://github.com/ruby/ruby/blob/trunk/proc.c#L1593
 VALUE
 rb_method_call(int argc, VALUE *argv, VALUE method)
 {
+    VALUE proc = rb_block_given_p() ? rb_block_proc() : Qnil;
+    return rb_method_call_with_block(argc, argv, method, proc);
+}
+
+VALUE
+rb_method_call_with_block(int argc, VALUE *argv, VALUE method, VALUE pass_procval)
+{
     VALUE result = Qnil;	/* OK */
     struct METHOD *data;
     int state;
@@ -1612,8 +1619,15 @@ rb_method_call(int argc, VALUE *argv, VA https://github.com/ruby/ruby/blob/trunk/proc.c#L1619
     }
     if ((state = EXEC_TAG()) == 0) {
 	rb_thread_t *th = GET_THREAD();
+	rb_block_t *block = 0;
+
+	if (!NIL_P(pass_procval)) {
+	    rb_proc_t *pass_proc;
+	    GetProcPtr(pass_procval, pass_proc);
+	    block = &pass_proc->block;
+	}
 
-	PASS_PASSED_BLOCK_TH(th);
+	th->passed_block = block;
 	result = rb_vm_call(th, data->recv, data->id,  argc, argv, data->me, data->defined_class);
     }
     POP_TAG();
@@ -2062,11 +2076,10 @@ mlambda(VALUE method) https://github.com/ruby/ruby/blob/trunk/proc.c#L2076
 }
 
 static VALUE
-bmcall(VALUE args, VALUE method)
+bmcall(VALUE args, VALUE method, int argc, VALUE *argv, VALUE passed_proc)
 {
     volatile VALUE a;
     VALUE ret;
-    int argc;
 
     if (CLASS_OF(args) != rb_cArray) {
 	args = rb_ary_new3(1, args);
@@ -2075,7 +2088,7 @@ bmcall(VALUE args, VALUE method) https://github.com/ruby/ruby/blob/trunk/proc.c#L2088
     else {
 	argc = check_argc(RARRAY_LEN(args));
     }
-    ret = rb_method_call(argc, RARRAY_PTR(args), method);
+    ret = rb_method_call_with_block(argc, RARRAY_PTR(args), method, passed_proc);
     RB_GC_GUARD(a) = args;
     return ret;
 }
Index: test/ruby/test_proc.rb
===================================================================
--- test/ruby/test_proc.rb	(revision 41358)
+++ test/ruby/test_proc.rb	(revision 41359)
@@ -200,7 +200,6 @@ class TestProc < Test::Unit::TestCase https://github.com/ruby/ruby/blob/trunk/test/ruby/test_proc.rb#L200
 
   def test_block_persist_between_calls
     bug8341 = '[Bug #8341]'
-    skip bug8341
     o = Object.new
     def o.m1(top=true)
       if top

--
ML: ruby-changes@q...
Info: http://www.atdot.net/~ko1/quickml/

[前][次][番号順一覧][スレッド一覧]