diff options
Diffstat (limited to 'mrbgems/mruby-struct')
| -rw-r--r-- | mrbgems/mruby-struct/mrbgem.rake | 1 | ||||
| -rw-r--r-- | mrbgems/mruby-struct/src/struct.c | 60 | ||||
| -rw-r--r-- | mrbgems/mruby-struct/test/struct.rb | 35 |
3 files changed, 66 insertions, 30 deletions
diff --git a/mrbgems/mruby-struct/mrbgem.rake b/mrbgems/mruby-struct/mrbgem.rake index 3e9eab8d7..2826ad2ad 100644 --- a/mrbgems/mruby-struct/mrbgem.rake +++ b/mrbgems/mruby-struct/mrbgem.rake @@ -1,4 +1,5 @@ MRuby::Gem::Specification.new('mruby-struct') do |spec| spec.license = 'MIT' spec.author = 'mruby developers' + spec.summary = 'standard Struct class' end diff --git a/mrbgems/mruby-struct/src/struct.c b/mrbgems/mruby-struct/src/struct.c index a8511fc3c..4f4c3533e 100644 --- a/mrbgems/mruby-struct/src/struct.c +++ b/mrbgems/mruby-struct/src/struct.c @@ -10,7 +10,6 @@ #include "mruby/array.h" #include "mruby/string.h" #include "mruby/class.h" -#include "mruby/data.h" #include "mruby/variable.h" #define RSTRUCT_ARY(st) mrb_ary_ptr(st) @@ -49,7 +48,7 @@ mrb_struct_iv_get(mrb_state *mrb, mrb_value c, const char *name) mrb_value mrb_struct_s_members(mrb_state *mrb, mrb_value klass) { - mrb_value members = struct_ivar_get(mrb, klass, mrb_intern2(mrb, "__members__", 11)); + mrb_value members = struct_ivar_get(mrb, klass, mrb_intern_lit(mrb, "__members__")); if (mrb_nil_p(members)) { mrb_raise(mrb, E_TYPE_ERROR, "uninitialized struct"); @@ -125,7 +124,7 @@ mrb_struct_getmember(mrb_state *mrb, mrb_value obj, mrb_sym id) return ptr[i]; } } - mrb_raisef(mrb, E_INDEX_ERROR, "%S is not struct member", mrb_sym2str(mrb, id)); + mrb_raisef(mrb, E_INDEX_ERROR, "`%S' is not a struct member", mrb_sym2str(mrb, id)); return mrb_nil_value(); /* not reached */ } @@ -167,16 +166,16 @@ mrb_id_attrset(mrb_state *mrb, mrb_sym id) { const char *name; char *buf; - size_t len; + mrb_int len; mrb_sym mid; name = mrb_sym2name_len(mrb, id, &len); - buf = (char *)mrb_malloc(mrb, len+2); - memcpy(buf, name, len); + buf = (char *)mrb_malloc(mrb, (size_t)len+2); + memcpy(buf, name, (size_t)len); buf[len] = '='; buf[len+1] = '\0'; - mid = mrb_intern2(mrb, buf, len+1); + mid = mrb_intern(mrb, buf, len+1); mrb_free(mrb, buf); return mid; } @@ -186,12 +185,13 @@ mrb_struct_set(mrb_state *mrb, mrb_value obj, mrb_value val) { const char *name; size_t i, len; + mrb_int slen; mrb_sym mid; mrb_value members, slot, *ptr, *ptr_members; /* get base id */ - name = mrb_sym2name_len(mrb, mrb->c->ci->mid, &len); - mid = mrb_intern2(mrb, name, len-1); /* omit last "=" */ + name = mrb_sym2name_len(mrb, mrb->c->ci->mid, &slen); + mid = mrb_intern(mrb, name, slen-1); /* omit last "=" */ members = mrb_struct_members(mrb, obj); ptr_members = RARRAY_PTR(members); @@ -203,9 +203,8 @@ mrb_struct_set(mrb_state *mrb, mrb_value obj, mrb_value val) return ptr[i] = val; } } - mrb_raisef(mrb, E_INDEX_ERROR, "`%S' is not a struct member", - mrb_sym2str(mrb, mid)); - return mrb_nil_value(); /* not reached */ + mrb_raisef(mrb, E_INDEX_ERROR, "`%S' is not a struct member", mrb_sym2str(mrb, mid)); + return mrb_nil_value(); /* not reached */ } static mrb_value @@ -217,15 +216,15 @@ mrb_struct_set_m(mrb_state *mrb, mrb_value obj) return mrb_struct_set(mrb, obj, val); } -#define is_notop_id(id) (id)//((id)>tLAST_TOKEN) -#define is_local_id(id) (is_notop_id(id))//&&((id)&ID_SCOPE_MASK)==ID_LOCAL) +#define is_notop_id(id) (id) /* ((id)>tLAST_TOKEN) */ +#define is_local_id(id) (is_notop_id(id)) /* &&((id)&ID_SCOPE_MASK)==ID_LOCAL) */ int mrb_is_local_id(mrb_sym id) { return is_local_id(id); } -#define is_const_id(id) (is_notop_id(id))//&&((id)&ID_SCOPE_MASK)==ID_CONST) +#define is_const_id(id) (is_notop_id(id)) /* &&((id)&ID_SCOPE_MASK)==ID_CONST) */ int mrb_is_const_id(mrb_sym id) { @@ -239,6 +238,7 @@ make_struct(mrb_state *mrb, mrb_value name, mrb_value members, struct RClass * k mrb_sym id; mrb_int i, len; struct RClass *c; + int ai; if (mrb_nil_p(name)) { c = mrb_class_new(mrb, klass); @@ -252,20 +252,21 @@ make_struct(mrb_state *mrb, mrb_value name, mrb_value members, struct RClass * k } if (mrb_const_defined_at(mrb, klass, id)) { mrb_warn(mrb, "redefining constant Struct::%S", name); - //?rb_mod_remove_const(klass, mrb_sym2name(mrb, id)); + /* ?rb_mod_remove_const(klass, mrb_sym2name(mrb, id)); */ } c = mrb_define_class_under(mrb, klass, RSTRING_PTR(name), klass); } MRB_SET_INSTANCE_TT(c, MRB_TT_ARRAY); nstr = mrb_obj_value(c); - mrb_iv_set(mrb, nstr, mrb_intern2(mrb, "__members__", 11), members); + mrb_iv_set(mrb, nstr, mrb_intern_lit(mrb, "__members__"), members); mrb_define_class_method(mrb, c, "new", mrb_instance_new, MRB_ARGS_ANY()); mrb_define_class_method(mrb, c, "[]", mrb_instance_new, MRB_ARGS_ANY()); mrb_define_class_method(mrb, c, "members", mrb_struct_s_members_m, MRB_ARGS_NONE()); - //RSTRUCT(nstr)->basic.c->super = c->c; + /* RSTRUCT(nstr)->basic.c->super = c->c; */ ptr_members = RARRAY_PTR(members); len = RARRAY_LEN(members); + ai = mrb_gc_arena_save(mrb); for (i=0; i< len; i++) { mrb_sym id = mrb_symbol(ptr_members[i]); if (mrb_is_local_id(id) || mrb_is_const_id(id)) { @@ -276,6 +277,7 @@ make_struct(mrb_state *mrb, mrb_value name, mrb_value members, struct RClass * k mrb_define_method_id(mrb, c, id, mrb_struct_ref, MRB_ARGS_NONE()); } mrb_define_method_id(mrb, c, mrb_id_attrset(mrb, id), mrb_struct_set_m, MRB_ARGS_REQ(1)); + mrb_gc_arena_restore(mrb, ai); } } return nstr; @@ -294,7 +296,7 @@ mrb_struct_define(mrb_state *mrb, const char *name, ...) va_start(ar, name); while ((mem = va_arg(ar, char*)) != 0) { - mrb_sym slot = mrb_intern(mrb, mem); + mrb_sym slot = mrb_intern_cstr(mrb, mem); mrb_ary_push(mrb, ary, mrb_symbol_value(slot)); } va_end(ar); @@ -382,7 +384,7 @@ mrb_struct_s_def(mrb_state *mrb, mrb_value klass) } st = make_struct(mrb, name, rest, struct_class(mrb)); if (!mrb_nil_p(b)) { - mrb_funcall(mrb, b, "call", 1, &st); + mrb_yield_with_class(mrb, b, 1, &st, st, mrb_class_ptr(klass)); } return st; @@ -393,7 +395,7 @@ num_members(mrb_state *mrb, struct RClass *klass) { mrb_value members; - members = struct_ivar_get(mrb, mrb_obj_value(klass), mrb_intern2(mrb, "__members__", 11)); + members = struct_ivar_get(mrb, mrb_obj_value(klass), mrb_intern_lit(mrb, "__members__")); if (!mrb_array_p(members)) { mrb_raise(mrb, E_TYPE_ERROR, "broken members"); } @@ -443,7 +445,7 @@ static mrb_value inspect_struct(mrb_state *mrb, mrb_value s, int recur) { const char *cn = mrb_class_name(mrb, mrb_obj_class(mrb, s)); - mrb_value members, str = mrb_str_new(mrb, "#<struct ", 9); + mrb_value members, str = mrb_str_new_lit(mrb, "#<struct "); mrb_value *ptr, *ptr_members; mrb_int i, len; @@ -451,7 +453,7 @@ inspect_struct(mrb_state *mrb, mrb_value s, int recur) mrb_str_append(mrb, str, mrb_str_new_cstr(mrb, cn)); } if (recur) { - return mrb_str_cat2(mrb, str, ":...>"); + return mrb_str_cat_lit(mrb, str, ":...>"); } members = mrb_struct_members(mrb, s); @@ -463,16 +465,16 @@ inspect_struct(mrb_state *mrb, mrb_value s, int recur) mrb_sym id; if (i > 0) { - mrb_str_cat2(mrb, str, ", "); + mrb_str_cat_lit(mrb, str, ", "); } else if (cn) { - mrb_str_cat2(mrb, str, " "); + mrb_str_cat_lit(mrb, str, " "); } slot = ptr_members[i]; id = mrb_symbol(slot); if (mrb_is_local_id(id) || mrb_is_const_id(id)) { const char *name; - size_t len; + mrb_int len; name = mrb_sym2name_len(mrb, id, &len); mrb_str_append(mrb, str, mrb_str_new(mrb, name, len)); @@ -480,10 +482,10 @@ inspect_struct(mrb_state *mrb, mrb_value s, int recur) else { mrb_str_append(mrb, str, mrb_inspect(mrb, slot)); } - mrb_str_cat2(mrb, str, "="); + mrb_str_cat_lit(mrb, str, "="); mrb_str_append(mrb, str, mrb_inspect(mrb, ptr[i])); } - mrb_str_cat2(mrb, str, ">"); + mrb_str_cat_lit(mrb, str, ">"); return str; } @@ -507,7 +509,7 @@ mrb_value mrb_struct_init_copy(mrb_state *mrb, mrb_value copy) { mrb_value s; - int i, len; + mrb_int i, len; mrb_get_args(mrb, "o", &s); diff --git a/mrbgems/mruby-struct/test/struct.rb b/mrbgems/mruby-struct/test/struct.rb index d79b30c0e..d647cd3a3 100644 --- a/mrbgems/mruby-struct/test/struct.rb +++ b/mrbgems/mruby-struct/test/struct.rb @@ -73,5 +73,38 @@ if Object.const_defined?(:Struct) cc = c.new(1,2) cc.select{|v| v % 2 == 0} == [2] end -end + assert('large struct') do + c = Struct.new(:m1, :m2, :m3, :m4, :m5, :m6, :m7, :m8, :m9, :m10, :m11, :m12, :m13) + cc = c.new(1,2,3,4,5,6,7,8,9,10,11,12,13) + assert_equal 1, cc.m1 + assert_equal 2, cc.m2 + assert_equal 3, cc.m3 + assert_equal 4, cc.m4 + assert_equal 5, cc.m5 + assert_equal 6, cc.m6 + assert_equal 7, cc.m7 + assert_equal 8, cc.m8 + assert_equal 9, cc.m9 + assert_equal 10, cc.m10 + assert_equal 13, cc.m13 + + cc.m13 = 'test' + assert_equal 'test', cc.m13 + + assert_raise(NoMethodError) { cc.m14 } + end + + assert('wrong struct arg count') do + c = Struct.new(:m1) + assert_raise ArgumentError do + cc = c.new(1,2,3) + end + end + + assert('struct inspect') do + c = Struct.new(:m1, :m2, :m3, :m4, :m5) + cc = c.new(1,2,3,4,5) + assert_equal "#<struct #{c.inspect} m1=1, m2=2, m3=3, m4=4, m5=5>", cc.inspect + end +end |
