diff options
| author | Yukihiro "Matz" Matsumoto <[email protected]> | 2015-07-13 07:08:01 +0900 |
|---|---|---|
| committer | Yukihiro "Matz" Matsumoto <[email protected]> | 2015-07-13 11:07:59 +0900 |
| commit | 9c311ddc938ad2cc88e4119374e47cd496e15a94 (patch) | |
| tree | 12589cca2f3b80cb16ad072b17e020ecd5003daa /src/class.c | |
| parent | 4dac03cb2d53227bde2e5f50e70ca79596807e11 (diff) | |
| download | mruby-9c311ddc938ad2cc88e4119374e47cd496e15a94.tar.gz mruby-9c311ddc938ad2cc88e4119374e47cd496e15a94.zip | |
refactor mrb_bob_missing to share raising NoMethodError code; fix #2878
Note: arguments of mrb_no_method_error() has changed. You need to replace
3rd and 4th argument (say n, argv) to mrb_ary_new_from_values(mrb, n, argv).
Diffstat (limited to 'src/class.c')
| -rw-r--r-- | src/class.c | 45 |
1 files changed, 26 insertions, 19 deletions
diff --git a/src/class.c b/src/class.c index e9cbc592d..0f9a77b2a 100644 --- a/src/class.c +++ b/src/class.c @@ -1262,6 +1262,31 @@ mrb_bob_not(mrb_state *mrb, mrb_value cv) return mrb_bool_value(!mrb_test(cv)); } +void +mrb_method_missing(mrb_state *mrb, mrb_sym name, mrb_value self, mrb_value args) +{ + mrb_sym inspect; + mrb_value repr; + + inspect = mrb_intern_lit(mrb, "inspect"); + if (mrb->c->ci > mrb->c->cibase && mrb->c->ci[-1].mid == inspect) { + /* method missing in inspect; avoid recursion */ + repr = mrb_any_to_s(mrb, self); + } + else if (mrb_respond_to(mrb, self, inspect) && mrb->c->ci - mrb->c->cibase < 64) { + repr = mrb_funcall_argv(mrb, self, inspect, 0, 0); + if (mrb_string_p(repr) && RSTRING_LEN(repr) > 64) { + repr = mrb_any_to_s(mrb, self); + } + } + else { + repr = mrb_any_to_s(mrb, self); + } + + mrb_no_method_error(mrb, name, args, "undefined method '%S' for %S", + mrb_sym2str(mrb, name), repr); +} + /* 15.3.1.3.30 */ /* * call-seq: @@ -1301,27 +1326,9 @@ mrb_bob_missing(mrb_state *mrb, mrb_value mod) mrb_sym name; mrb_value *a; mrb_int alen; - mrb_sym inspect; - mrb_value repr; mrb_get_args(mrb, "n*", &name, &a, &alen); - - inspect = mrb_intern_lit(mrb, "inspect"); - if (mrb->c->ci > mrb->c->cibase && mrb->c->ci[-1].mid == inspect) { - /* method missing in inspect; avoid recursion */ - repr = mrb_any_to_s(mrb, mod); - } - else if (mrb_respond_to(mrb, mod, inspect) && mrb->c->ci - mrb->c->cibase < 64) { - repr = mrb_funcall_argv(mrb, mod, inspect, 0, 0); - if (mrb_string_p(repr) && RSTRING_LEN(repr) > 64) { - repr = mrb_any_to_s(mrb, mod); - } - } - else { - repr = mrb_any_to_s(mrb, mod); - } - - mrb_no_method_error(mrb, name, alen, a, "undefined method '%S' for %S", mrb_sym2str(mrb, name), repr); + mrb_method_missing(mrb, name, mod, mrb_ary_new_from_values(mrb, alen, a)); /* not reached */ return mrb_nil_value(); } |
