From d265c03da0a4a1f8fe3bd20d69c0f78588ec8aff Mon Sep 17 00:00:00 2001 From: ksss Date: Thu, 8 Sep 2016 16:18:48 +0900 Subject: Fix SEGV when splat object Splat operation should return an array. And raise an error if result of convert by to_a is not array or nil. --- src/array.c | 23 ++++++++++++++++++++--- 1 file changed, 20 insertions(+), 3 deletions(-) diff --git a/src/array.c b/src/array.c index 9b8a49584..df953832b 100644 --- a/src/array.c +++ b/src/array.c @@ -891,15 +891,32 @@ mrb_ary_rindex_m(mrb_state *mrb, mrb_value self) MRB_API mrb_value mrb_ary_splat(mrb_state *mrb, mrb_value v) { + mrb_value a, recv_class; + if (mrb_array_p(v)) { return v; } - if (mrb_respond_to(mrb, v, mrb_intern_lit(mrb, "to_a"))) { - return mrb_funcall(mrb, v, "to_a", 0); + + if (!mrb_respond_to(mrb, v, mrb_intern_lit(mrb, "to_a"))) { + return mrb_ary_new_from_values(mrb, 1, &v); } - else { + + a = mrb_funcall(mrb, v, "to_a", 0); + if (mrb_array_p(a)) { + return a; + } + else if (mrb_nil_p(a)) { return mrb_ary_new_from_values(mrb, 1, &v); } + else { + recv_class = mrb_obj_value(mrb_obj_class(mrb, v)); + mrb_raisef(mrb, E_TYPE_ERROR, "can't convert %S to Array (%S#to_a gives %S)", + recv_class, + recv_class, + mrb_obj_value(mrb_obj_class(mrb, a)) + ); + return mrb_undef_value(); + } } static mrb_value -- cgit v1.2.3