Revision: 422 http://trac.macosforge.org/projects/ruby/changeset/422 Author: lsansonetti@apple.com Date: 2008-08-12 18:10:29 -0700 (Tue, 12 Aug 2008) Log Message: ----------- wip Modified Paths: -------------- MacRuby/branches/lrz_unstable/class.c MacRuby/branches/lrz_unstable/compile.c MacRuby/branches/lrz_unstable/include/ruby/ruby.h MacRuby/branches/lrz_unstable/objc.m MacRuby/branches/lrz_unstable/object.c MacRuby/branches/lrz_unstable/variable.c MacRuby/branches/lrz_unstable/vm_eval.c MacRuby/branches/lrz_unstable/vm_insnhelper.c Modified: MacRuby/branches/lrz_unstable/class.c =================================================================== --- MacRuby/branches/lrz_unstable/class.c 2008-08-12 06:00:09 UTC (rev 421) +++ MacRuby/branches/lrz_unstable/class.c 2008-08-13 01:10:29 UTC (rev 422) @@ -121,7 +121,6 @@ VALUE klass; klass = rb_objc_alloc_class(name, super, T_CLASS, rb_cClass); - objc_registerClassPair((Class)klass); if (RCLASS_SUPER(klass) == rb_cNSObject) { @@ -230,28 +229,30 @@ rb_mod_init_copy(VALUE clone, VALUE orig) { rb_obj_init_copy(clone, orig); +#if !WITH_OBJC if (!RCLASS_SINGLETON(CLASS_OF(clone))) { RBASIC(clone)->klass = rb_singleton_class_clone(orig); } +#endif #if WITH_OBJC { - Class ocsuper; + VALUE super; int version_flag; if (orig == rb_cNSMutableString || orig == rb_cNSMutableArray || orig == rb_cNSMutableHash) { - ocsuper = (Class)orig; + super = orig; rb_warn("cloning class `%s' is not supported, creating a " \ "subclass instead", rb_class2name(orig)); } else { - ocsuper = class_getSuperclass((Class)orig); + super = RCLASS_SUPER(orig); } - class_setSuperclass((Class)clone, ocsuper); + RCLASS_SUPER(clone) = super; version_flag = RCLASS_IS_RUBY_CLASS; - if ((RCLASS_VERSION(ocsuper) & RCLASS_IS_OBJECT_SUBCLASS) == RCLASS_IS_OBJECT_SUBCLASS) + if ((RCLASS_VERSION(super) & RCLASS_IS_OBJECT_SUBCLASS) == RCLASS_IS_OBJECT_SUBCLASS) version_flag |= RCLASS_IS_OBJECT_SUBCLASS; class_setVersion((Class)clone, version_flag); @@ -370,26 +371,21 @@ return rb_cClass; } else { -// VALUE metasuper; VALUE klass; klass = rb_class_boot(super); RBASIC(obj)->klass = klass; #if WITH_OBJC - //RCLASS_SET_SINGLETON(klass); + if (super == rb_cNSObject) { + RCLASS_VERSION(klass) ^= RCLASS_IS_OBJECT_SUBCLASS; + } + RCLASS_SET_VERSION_FLAG(klass, RCLASS_IS_SINGLETON); #else FL_SET(klass, FL_SINGLETON); #endif rb_singleton_class_attached(klass, obj); -#if 0 - metasuper = RBASIC(rb_class_real(super))->klass; - /* metaclass of a superclass may be NULL at boot time */ - if (metasuper) { - RBASIC(klass)->klass = metasuper; - } -#endif return klass; } } @@ -1190,29 +1186,22 @@ } DEFER_INTS; -#if WITH_OBJC - if (NATIVE(obj)) { - Class ocklass; - - ocklass = *(Class *)obj; - klass = (VALUE)ocklass; - if (class_isMetaClass(ocklass)) - return klass; - - if (!RCLASS_SINGLETON(ocklass)) - klass = rb_make_metaclass(obj, (VALUE)ocklass); - - return klass; - } - if (TYPE(obj) == T_CLASS) - return obj; -#endif if (RCLASS_SINGLETON(RBASIC(obj)->klass) && rb_iv_get(RBASIC(obj)->klass, "__attached__") == obj) { klass = RBASIC(obj)->klass; } else { - klass = rb_make_metaclass(obj, RBASIC(obj)->klass); +#if WITH_OBJC + switch (TYPE(obj)) { + case T_CLASS: + case T_MODULE: + klass = *(VALUE *)obj; + break; + default: + klass = rb_make_metaclass(obj, RBASIC(obj)->klass); + break; + } +#endif } #if 0 if (OBJ_TAINTED(obj)) { Modified: MacRuby/branches/lrz_unstable/compile.c =================================================================== --- MacRuby/branches/lrz_unstable/compile.c 2008-08-12 06:00:09 UTC (rev 421) +++ MacRuby/branches/lrz_unstable/compile.c 2008-08-13 01:10:29 UTC (rev 422) @@ -732,7 +732,7 @@ mcache->as.rcall.sel = sel_registerName(buf); } } - operands[4] = (VALUE)mcache; + GC_WB(&operands[4], mcache); iobj = new_insn_core(iseq, line_no, BIN(send), 5, operands); return iobj; } Modified: MacRuby/branches/lrz_unstable/include/ruby/ruby.h =================================================================== --- MacRuby/branches/lrz_unstable/include/ruby/ruby.h 2008-08-12 06:00:09 UTC (rev 421) +++ MacRuby/branches/lrz_unstable/include/ruby/ruby.h 2008-08-13 01:10:29 UTC (rev 422) @@ -499,7 +499,7 @@ # define RCLASS_IS_OBJECT_SUBCLASS 0x100 /* class is a true RBObject subclass */ # define RCLASS_IS_RUBY_CLASS 0x200 /* class was created from Ruby */ # define RCLASS_IS_MODULE 0x400 /* class represents a Ruby Module */ -# define RCLASS_IS_SINGLETON 0x800 /* class represents a singleton/metaclass */ +# define RCLASS_IS_SINGLETON 0x800 /* class represents a singleton */ # define RCLASS_IS_FROZEN 0x1000 /* class is frozen */ # define RCLASS_IS_TAINTED 0x2000 /* class is tainted */ # define RCLASS_IS_STRING_SUBCLASS 0x10000 /* class is a subclass of NSCFString */ @@ -509,16 +509,17 @@ # define RCLASS_VERSION(m) (class_getVersion((Class)m)) # define RCLASS_SET_VERSION_FLAG(m,f) (class_setVersion((Class)m, (RCLASS_VERSION(m) | f))) # define RCLASS_SUPER(m) (class_getSuperclass((Class)m)) -# define RCLASS_SINGLETON(m) (class_isMetaclass((Class)m)) +# define RCLASS_META(m) (class_isMetaclass((Class)m)) # else # define RCLASS_VERSION(m) (*(long *)((void *)m + (sizeof(void *) * 3))) # define RCLASS_SET_VERSION_FLAG(m,f) (RCLASS_VERSION(m) |= f) # define RCLASS_SUPER(m) (*(VALUE *)((void *)m + (sizeof(void *) * 1))) # define _RCLASS_INFO(m) (*(long *)((void *)m + (sizeof(void *) * 4))) -# define RCLASS_SINGLETON(m) (_RCLASS_INFO(m) & CLS_META) +# define RCLASS_META(m) (_RCLASS_INFO(m) & CLS_META) # endif # define RCLASS_RUBY(m) ((RCLASS_VERSION(m) & RCLASS_IS_RUBY_CLASS) == RCLASS_IS_RUBY_CLASS) # define RCLASS_MODULE(m) ((RCLASS_VERSION(m) & RCLASS_IS_MODULE) == RCLASS_IS_MODULE) +# define RCLASS_SINGLETON(m) ((RCLASS_VERSION(m) & RCLASS_IS_SINGLETON) == RCLASS_IS_SINGLETON) CFMutableDictionaryRef rb_class_ivar_dict(VALUE); CFMutableDictionaryRef rb_class_ivar_dict_or_create(VALUE); void rb_class_ivar_set_dict(VALUE, CFMutableDictionaryRef); @@ -1181,7 +1182,7 @@ } #if WITH_OBJC else if ((k = *(Class *)obj) != NULL) { - if (RCLASS_SINGLETON(k)) { + if (RCLASS_META(k)) { if (RCLASS_MODULE(obj)) return T_MODULE; else return T_CLASS; } Modified: MacRuby/branches/lrz_unstable/objc.m =================================================================== --- MacRuby/branches/lrz_unstable/objc.m 2008-08-12 06:00:09 UTC (rev 421) +++ MacRuby/branches/lrz_unstable/objc.m 2008-08-13 01:10:29 UTC (rev 422) @@ -1722,12 +1722,25 @@ static ID rb_bs_struct_field_ivar_id(void) { + const char *frame_str; char ivar_name[128]; - int len; + size_t len; - len = snprintf(ivar_name, sizeof ivar_name, "@%s", - rb_id2name(rb_frame_this_func())); - if (ivar_name[len - 1] == '=') + frame_str = rb_id2name(rb_frame_this_func()); + if (strlen(frame_str) >= 5 + && frame_str[0] == 's' + && frame_str[1] == 'e' + && frame_str[2] == 't' + && isupper(frame_str[3])) { + + len = snprintf(ivar_name, sizeof ivar_name, "@%s", &frame_str[3]); + ivar_name[1] = tolower(ivar_name[1]); + } + else { + len = snprintf(ivar_name, sizeof ivar_name, "@%s", frame_str); + } + + if (ivar_name[len - 1] == '=' || ivar_name[len - 1] == ':') ivar_name[len - 1] = '\0'; return rb_intern(ivar_name); Modified: MacRuby/branches/lrz_unstable/object.c =================================================================== --- MacRuby/branches/lrz_unstable/object.c 2008-08-12 06:00:09 UTC (rev 421) +++ MacRuby/branches/lrz_unstable/object.c 2008-08-13 01:10:29 UTC (rev 422) @@ -131,6 +131,11 @@ rb_class_real(VALUE cl) { #if WITH_OBJC + if (cl == 0) + return 0; + while (RCLASS_SINGLETON(cl)) { + cl = RCLASS_SUPER(cl); + } return cl; #else if (cl == 0) @@ -937,6 +942,7 @@ || rb_objc_flag_check((const void *)obj, FL_FREEZE) ? Qtrue : Qfalse; case T_CLASS: + case T_ICLASS: case T_MODULE: return (RCLASS_VERSION(obj) & RCLASS_IS_FROZEN) == RCLASS_IS_FROZEN ? Qtrue : Qfalse; default: @@ -2508,6 +2514,12 @@ { return NATIVE(recv) ? Qtrue : Qfalse; } + +static VALUE +rb_class_is_meta(VALUE klass) +{ + return RCLASS_META(klass) ? Qtrue : Qfalse; +} #endif /* @@ -2729,6 +2741,7 @@ rb_define_method(rb_cModule, "ancestors", rb_mod_ancestors, 0); /* in class.c */ #if WITH_OBJC rb_define_private_method(rb_cModule, "ib_outlet", rb_mod_objc_ib_outlet, -1); /* in objc.m */ + rb_define_method(rb_cClass, "__meta__?", rb_class_is_meta, 0); #endif rb_define_private_method(rb_cModule, "attr", rb_mod_attr, -1); Modified: MacRuby/branches/lrz_unstable/variable.c =================================================================== --- MacRuby/branches/lrz_unstable/variable.c 2008-08-12 06:00:09 UTC (rev 421) +++ MacRuby/branches/lrz_unstable/variable.c 2008-08-13 01:10:29 UTC (rev 422) @@ -1246,7 +1246,7 @@ if (!CFDictionaryGetValueIfPresent( (CFDictionaryRef)ROBJECT(obj)->ivars.as.tbl, (const void *)id, - (const void **)val)) + (const void **)&val)) val = Qundef; break; } @@ -1259,6 +1259,7 @@ if (len <= index) break; val = ptr[index]; #endif + if (val != Qundef) return val; break; @@ -1363,6 +1364,7 @@ xfree(ROBJECT(obj)->ivars.as.ary); GC_WB(&ROBJECT(obj)->ivars.as.tbl, tbl); + CFMakeCollectable(tbl); RB_IVAR_SET_TYPE(ROBJECT(obj)->ivars, RB_IVAR_TBL); } else { @@ -2427,6 +2429,10 @@ #endif tmp = klass; +#if WITH_OBJC + if (!RCLASS_META(klass)) + tmp = klass = *(VALUE *)klass; +#endif CVAR_LOOKUP(0, {if (!front) front = klass; target = klass;}); if (target) { if (front && target != front) { @@ -2461,6 +2467,10 @@ #endif tmp = klass; +#if WITH_OBJC + if (!RCLASS_META(klass)) + tmp = klass = *(VALUE *)klass; +#endif CVAR_LOOKUP(&value, {if (!front) front = klass; target = klass;}); if (!target) { rb_name_error(id,"uninitialized class variable %s in %s", @@ -2492,6 +2502,10 @@ CFMutableDictionaryRef iv_dict; #endif if (!klass) return Qfalse; +#if WITH_OBJC + if (!RCLASS_META(klass)) + klass = *(VALUE *)klass; +#endif CVAR_LOOKUP(0,return Qtrue); return Qfalse; } Modified: MacRuby/branches/lrz_unstable/vm_eval.c =================================================================== --- MacRuby/branches/lrz_unstable/vm_eval.c 2008-08-12 06:00:09 UTC (rev 421) +++ MacRuby/branches/lrz_unstable/vm_eval.c 2008-08-13 01:10:29 UTC (rev 422) @@ -198,10 +198,25 @@ SEL sel; if (argc > 0 && mid != ID_ALLOCATOR) { + const char *mid_str; char buf[512]; - strncpy(buf, rb_id2name(mid), sizeof buf); - if (buf[strlen(buf) - 1] != ':') - strlcat(buf, ":", sizeof buf); + size_t len; + + mid_str = rb_id2name(mid); + len = strlen(mid_str); + if (len > 1 && mid_str[len - 1] == '=' && isalpha(mid_str[len - 2])) { + assert(len + 3 < sizeof(buf)); + buf[0] = 's'; + buf[1] = 'e'; + buf[2] = 't'; + buf[3] = toupper(mid_str[0]); + strlcpy(&buf[4], &mid_str[1], len - 1); + buf[len + 2] = ':'; + buf[len + 3] = '\0'; + } + else if (mid_str[len - 1] != ':') { + snprintf(buf, sizeof buf, "%s:", mid_str); + } mid = rb_intern(buf); } Modified: MacRuby/branches/lrz_unstable/vm_insnhelper.c =================================================================== --- MacRuby/branches/lrz_unstable/vm_insnhelper.c 2008-08-12 06:00:09 UTC (rev 421) +++ MacRuby/branches/lrz_unstable/vm_insnhelper.c 2008-08-13 01:10:29 UTC (rev 422) @@ -674,7 +674,7 @@ SEL sel; IMP imp; mn = rb_objc_method_node(klass, id, &imp, &sel); - if (imp != NULL) { + if (mn == NULL && imp != NULL) { static struct rb_method_cache mcache_s; mcache = &mcache_s; mcache->as.ocall.sel = sel;
participants (1)
-
source_changes@macosforge.org