From 1ec5994377b45b0299a9c4e6e7ab275792d81bc9 Mon Sep 17 00:00:00 2001 From: Francois Chagnon Date: Mon, 14 Nov 2016 16:49:45 -0500 Subject: Fix calling .arity on Proc with undefined `initialize` Reported by @bouk --- mrbgems/mruby-proc-ext/src/proc.c | 3 +++ mrbgems/mruby-proc-ext/test/proc.rb | 11 +++++++++++ 2 files changed, 14 insertions(+) (limited to 'mrbgems/mruby-proc-ext') diff --git a/mrbgems/mruby-proc-ext/src/proc.c b/mrbgems/mruby-proc-ext/src/proc.c index c8c8f1aa1..34f6230dc 100644 --- a/mrbgems/mruby-proc-ext/src/proc.c +++ b/mrbgems/mruby-proc-ext/src/proc.c @@ -114,6 +114,9 @@ mrb_proc_parameters(mrb_state *mrb, mrb_value self) // TODO cfunc aspec is not implemented yet return mrb_ary_new(mrb); } + if (!irep) { + return mrb_ary_new(mrb); + } if (!irep->lv) { return mrb_ary_new(mrb); } diff --git a/mrbgems/mruby-proc-ext/test/proc.rb b/mrbgems/mruby-proc-ext/test/proc.rb index 75e11dd93..7a078aabf 100644 --- a/mrbgems/mruby-proc-ext/test/proc.rb +++ b/mrbgems/mruby-proc-ext/test/proc.rb @@ -58,6 +58,17 @@ assert('Proc#parameters') do assert_equal([[:req, :a], [:req, :b], [:opt, :c], [:opt, :d], [:rest, :e], [:req, :f], [:req, :g], [:block, :h]], lambda {|a,b,c=:c,d=:d,*e,f,g,&h|}.parameters) end +assert('Proc#parameters with uninitialized Proc') do + begin + Proc.alias_method(:original_initialize, :initialize) + Proc.remove_method(:initialize) + assert_equal [], Proc.new{|a, b, c| 1}.parameters + ensure + Proc.alias_method(:initialize, :original_initialize) + Proc.remove_method(:original_initialize) + end +end + assert('Proc#to_proc') do proc = Proc.new {} assert_equal proc, proc.to_proc -- cgit v1.2.3 From 3cba13c249457cfb318c9d7d4456d99003442139 Mon Sep 17 00:00:00 2001 From: ksss Date: Wed, 21 Dec 2016 15:17:05 +0900 Subject: Proc shouldn't have `initialize` method Fix #3356 --- mrbgems/mruby-proc-ext/test/proc.rb | 11 ----------- src/proc.c | 12 ++++++------ test/t/proc.rb | 27 --------------------------- 3 files changed, 6 insertions(+), 44 deletions(-) (limited to 'mrbgems/mruby-proc-ext') diff --git a/mrbgems/mruby-proc-ext/test/proc.rb b/mrbgems/mruby-proc-ext/test/proc.rb index 7a078aabf..75e11dd93 100644 --- a/mrbgems/mruby-proc-ext/test/proc.rb +++ b/mrbgems/mruby-proc-ext/test/proc.rb @@ -58,17 +58,6 @@ assert('Proc#parameters') do assert_equal([[:req, :a], [:req, :b], [:opt, :c], [:opt, :d], [:rest, :e], [:req, :f], [:req, :g], [:block, :h]], lambda {|a,b,c=:c,d=:d,*e,f,g,&h|}.parameters) end -assert('Proc#parameters with uninitialized Proc') do - begin - Proc.alias_method(:original_initialize, :initialize) - Proc.remove_method(:initialize) - assert_equal [], Proc.new{|a, b, c| 1}.parameters - ensure - Proc.alias_method(:initialize, :original_initialize) - Proc.remove_method(:original_initialize) - end -end - assert('Proc#to_proc') do proc = Proc.new {} assert_equal proc, proc.to_proc diff --git a/src/proc.c b/src/proc.c index 470547094..0fb38359f 100644 --- a/src/proc.c +++ b/src/proc.c @@ -148,19 +148,19 @@ mrb_proc_copy(struct RProc *a, struct RProc *b) } static mrb_value -mrb_proc_initialize(mrb_state *mrb, mrb_value self) +mrb_proc_s_new(mrb_state *mrb, mrb_value proc_class) { mrb_value blk; + struct RProc *p; mrb_get_args(mrb, "&", &blk); if (mrb_nil_p(blk)) { /* Calling Proc.new without a block is not implemented yet */ mrb_raise(mrb, E_ARGUMENT_ERROR, "tried to create Proc object without a block"); } - else { - mrb_proc_copy(mrb_proc_ptr(self), mrb_proc_ptr(blk)); - } - return self; + p = (struct RProc *)mrb_obj_alloc(mrb, MRB_TT_PROC, mrb_class_ptr(proc_class)); + mrb_proc_copy(p, mrb_proc_ptr(blk)); + return mrb_obj_value(p); } static mrb_value @@ -268,7 +268,7 @@ mrb_init_proc(mrb_state *mrb) call_irep->iseq = call_iseq; call_irep->ilen = 1; - mrb_define_method(mrb, mrb->proc_class, "initialize", mrb_proc_initialize, MRB_ARGS_NONE()); + mrb_define_class_method(mrb, mrb->proc_class, "new", mrb_proc_s_new, MRB_ARGS_ANY()); mrb_define_method(mrb, mrb->proc_class, "initialize_copy", mrb_proc_init_copy, MRB_ARGS_REQ(1)); mrb_define_method(mrb, mrb->proc_class, "arity", mrb_proc_arity, MRB_ARGS_NONE()); diff --git a/test/t/proc.rb b/test/t/proc.rb index 29530e8dd..888b7d56a 100644 --- a/test/t/proc.rb +++ b/test/t/proc.rb @@ -46,17 +46,6 @@ assert('Proc#arity', '15.2.17.4.2') do assert_equal(-1, g) end -assert('Proc#arity with unitialized Proc') do - begin - Proc.alias_method(:original_initialize, :initialize) - Proc.remove_method(:initialize) - assert_equal 0, Proc.new{|a, b, c| 1}.arity - ensure - Proc.alias_method(:initialize, :original_initialize) - Proc.remove_method(:original_initialize) - end -end - assert('Proc#call', '15.2.17.4.3') do a = 0 b = Proc.new { a += 1 } @@ -163,19 +152,3 @@ assert('&obj call to_proc if defined') do assert_raise(TypeError){ mock(&(Object.new)) } end - -assert('initialize_copy works when initialize is removed') do - begin - Proc.alias_method(:old_initialize, :initialize) - Proc.remove_method(:initialize) - - a = Proc.new {} - b = Proc.new {} - assert_nothing_raised do - a.initialize_copy(b) - end - ensure - Proc.alias_method(:initialize, :old_initialize) - Proc.remove_method(:old_initialize) - end -end -- cgit v1.2.3