[macruby-changes] [3323] MacRuby/trunk

source_changes at macosforge.org source_changes at macosforge.org
Fri Jan 22 18:45:39 PST 2010


Revision: 3323
          http://trac.macosforge.org/projects/ruby/changeset/3323
Author:   lsansonetti at apple.com
Date:     2010-01-22 18:45:37 -0800 (Fri, 22 Jan 2010)
Log Message:
-----------
fix a const lookup bug in instance_eval, fix a deadlock when autoloading constants, fix a GC bug when passing thread-local objects to a new thread

Modified Paths:
--------------
    MacRuby/trunk/dispatcher.cpp
    MacRuby/trunk/eval.c
    MacRuby/trunk/include/ruby/intern.h
    MacRuby/trunk/vm.cpp
    MacRuby/trunk/vm.h
    MacRuby/trunk/vm_eval.c

Modified: MacRuby/trunk/dispatcher.cpp
===================================================================
--- MacRuby/trunk/dispatcher.cpp	2010-01-23 01:06:40 UTC (rev 3322)
+++ MacRuby/trunk/dispatcher.cpp	2010-01-23 02:45:37 UTC (rev 3323)
@@ -436,6 +436,11 @@
 	    return ((VALUE (*)(VALUE, SEL, ...))node->ruby_imp)
 		(self, sel, rb_ary_new4(argc, argv));
 	}
+	else if (arity.real == 3) {
+	    return ((VALUE (*)(VALUE, SEL, VALUE, int,
+			    const VALUE *))node->ruby_imp)
+		(self, sel, top, argc, argv);
+	}
 	else {
 	    printf("invalid negative arity for C function %d\n",
 		    arity.real);

Modified: MacRuby/trunk/eval.c
===================================================================
--- MacRuby/trunk/eval.c	2010-01-23 01:06:40 UTC (rev 3322)
+++ MacRuby/trunk/eval.c	2010-01-23 02:45:37 UTC (rev 3323)
@@ -506,8 +506,6 @@
  *  _mod_ or one of its ancestors. See also <code>Module#include</code>.
  */
 
-VALUE rb_make_singleton_class(VALUE super);
-
 static VALUE
 rb_mod_append_features(VALUE module, SEL sel, VALUE include)
 {

Modified: MacRuby/trunk/include/ruby/intern.h
===================================================================
--- MacRuby/trunk/include/ruby/intern.h	2010-01-23 01:06:40 UTC (rev 3322)
+++ MacRuby/trunk/include/ruby/intern.h	2010-01-23 02:45:37 UTC (rev 3323)
@@ -152,6 +152,7 @@
 bool rb_objc_install_primitives(Class ocklass, Class ocsuper);
 void rb_define_object_special_methods(VALUE klass);
 VALUE rb_class_new_instance_imp(VALUE, SEL, int, VALUE *);
+VALUE rb_make_singleton_class(VALUE super);
 #endif
 VALUE rb_class_boot(VALUE);
 VALUE rb_class_new(VALUE);

Modified: MacRuby/trunk/vm.cpp
===================================================================
--- MacRuby/trunk/vm.cpp	2010-01-23 01:06:40 UTC (rev 3322)
+++ MacRuby/trunk/vm.cpp	2010-01-23 02:45:37 UTC (rev 3323)
@@ -1143,8 +1143,15 @@
 	VALUE value;
 	if (CFDictionaryGetValueIfPresent(iv_dict, (const void *)id,
 		    (const void **)&value)) {
-	    if (value == Qundef && RTEST(rb_autoload_load(klass, id))) {
-		goto retry;
+	    if (value == Qundef) {
+		// Constant is a candidate for autoload. We must release the
+		// GIL before requiring the file and acquire it again.
+		GET_CORE()->unlock();
+		const bool autoloaded = RTEST(rb_autoload_load(klass, id));
+		GET_CORE()->lock();
+		if (autoloaded) {
+		    goto retry;
+		}
 	    }
 	    return value;
 	}
@@ -1281,6 +1288,22 @@
     return o == NULL ? Qundef : (VALUE)o->klass;
 }
 
+static VALUE
+get_klass_const(VALUE outer, ID path, bool lexical)
+{
+    if (lexical) {
+	if (rb_vm_const_lookup(outer, path, true, true) == Qtrue) {
+	    return rb_vm_const_lookup(outer, path, true, false);
+	}
+    }
+    else {
+	if (rb_const_defined_at(outer, path)) {
+	    return rb_const_get_at(outer, path);
+	}
+    }
+    return Qundef;
+}
+
 extern "C"
 VALUE
 rb_vm_define_class(ID path, VALUE outer, VALUE super, int flags,
@@ -1296,10 +1319,9 @@
 	}
     }
 
-    VALUE klass;
-    if (rb_const_defined_at(outer, path)) {
+    VALUE klass = get_klass_const(outer, path, dynamic_class);
+    if (klass != Qundef) {
 	// Constant is already defined.
-	klass = rb_const_get_at(outer, path);
 	check_if_module(klass);
 	if (!(flags & DEFINE_MODULE) && super != 0) {
 	    if (rb_class_real(RCLASS_SUPER(klass)) != super) {
@@ -4461,6 +4483,13 @@
     if (body != NULL) {
 	GC_WB(&t->body, body);
 	rb_vm_block_make_detachable_proc(body);
+
+	// Remove the thread-local bit of all dynamic variables.
+	for (int i = 0; i < body->dvars_size; i++) {
+	    VALUE *dvar = body->dvars[i];
+	    GC_RETAIN(*dvar);
+	    GC_RELEASE(*dvar);
+	}
     }
     else {
 	t->body = NULL;

Modified: MacRuby/trunk/vm.h
===================================================================
--- MacRuby/trunk/vm.h	2010-01-23 01:06:40 UTC (rev 3322)
+++ MacRuby/trunk/vm.h	2010-01-23 02:45:37 UTC (rev 3323)
@@ -231,6 +231,9 @@
 	    else if (argc == -2) {
 		arity.real = 1;
 	    }
+	    else if (argc == -3) {
+		arity.real = 3;
+	    }
 	    else {
 		printf("invalid FBODY arity: %d\n", argc);
 		abort();

Modified: MacRuby/trunk/vm_eval.c
===================================================================
--- MacRuby/trunk/vm_eval.c	2010-01-23 01:06:40 UTC (rev 3322)
+++ MacRuby/trunk/vm_eval.c	2010-01-23 02:45:37 UTC (rev 3323)
@@ -501,7 +501,7 @@
  */
 
 static VALUE
-rb_obj_instance_eval(VALUE self, SEL sel, int argc, VALUE *argv)
+rb_obj_instance_eval(VALUE self, SEL sel, VALUE top, int argc, VALUE *argv)
 {
     VALUE klass;
 
@@ -509,7 +509,30 @@
 	klass = 0;
     }
     else {
-	klass = rb_singleton_class(self);
+	switch (TYPE(self)) {
+#if 0
+	    case T_CLASS:
+	    case T_MODULE:
+		if (RCLASS_RUBY(self)) {
+		    VALUE sself = rb_make_singleton_class(RCLASS_SUPER(self));
+		    RCLASS_SET_SUPER(self, sself);
+		    self = sself;
+		}
+		else {
+		    klass = rb_singleton_class(self);
+		    break;
+		}
+		// fall through
+#endif
+	    default:
+		klass = rb_singleton_class(self);
+		switch (TYPE(top)) {
+		    case T_CLASS:
+		    case T_MODULE:
+			rb_vm_set_outer(klass, top);
+			break;
+		}
+	}
     }
     return specific_eval(argc, argv, klass, self);
 }
@@ -759,12 +782,12 @@
 
     rb_objc_define_module_function(rb_mKernel, "loop", rb_f_loop, 0);
 
-    rb_objc_define_method(rb_cNSObject, "instance_eval", rb_obj_instance_eval, -1);
+    rb_objc_define_method(rb_cNSObject, "instance_eval", rb_obj_instance_eval, -3);
     rb_objc_define_method(rb_cNSObject, "instance_exec", rb_obj_instance_exec, -1);
     rb_objc_define_private_method(rb_cNSObject, "method_missing", rb_method_missing, -1);
     rb_objc_define_method(rb_cNSObject, "__send__", rb_f_send, -1);
 
-    rb_objc_define_method(rb_cBasicObject, "instance_eval", rb_obj_instance_eval, -1);
+    rb_objc_define_method(rb_cBasicObject, "instance_eval", rb_obj_instance_eval, -3);
     rb_objc_define_method(rb_cBasicObject, "instance_exec", rb_obj_instance_exec, -1);
     rb_objc_define_private_method(rb_cBasicObject, "method_missing", rb_method_missing, -1);
     rb_objc_define_method(rb_cBasicObject, "__send__", rb_f_send, -1);
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.macosforge.org/pipermail/macruby-changes/attachments/20100122/aac19872/attachment-0001.html>


More information about the macruby-changes mailing list