[macruby-changes] [3940] MacRuby/trunk/vm.cpp

source_changes at macosforge.org source_changes at macosforge.org
Sun Apr 18 14:11:47 PDT 2010


Revision: 3940
          http://trac.macosforge.org/projects/ruby/changeset/3940
Author:   lsansonetti at apple.com
Date:     2010-04-18 14:11:41 -0700 (Sun, 18 Apr 2010)
Log Message:
-----------
disable lazy JIT in case the target class already has a custom Objective-C method resolver (CALayer is one)

Modified Paths:
--------------
    MacRuby/trunk/vm.cpp

Modified: MacRuby/trunk/vm.cpp
===================================================================
--- MacRuby/trunk/vm.cpp	2010-04-17 02:09:53 UTC (rev 3939)
+++ MacRuby/trunk/vm.cpp	2010-04-18 21:11:41 UTC (rev 3940)
@@ -2092,6 +2092,8 @@
     invalidate_respond_to_cache();
 }
 
+static bool class_has_custom_resolver(Class klass);
+
 static void
 prepare_method(Class klass, bool dynamic_class, SEL sel, void *data,
 	const rb_vm_arity_t &arity, int flags, bool precompiled)
@@ -2122,6 +2124,7 @@
 
     const char *sel_name = sel_getName(sel);
     const bool genuine_selector = sel_name[strlen(sel_name) - 1] == ':';
+    const bool custom_resolver = class_has_custom_resolver(klass);
     bool redefined = false;
     bool added_modfunc = false;
     SEL orig_sel = sel;
@@ -2144,8 +2147,9 @@
     }
     else {
 	Function *func = (Function *)data;
-	if (m != NULL) {
-	    // The method already exists - we need to JIT it.
+	if (m != NULL || custom_resolver) {
+	    // The method already exists _or_ the class implemented a custom
+	    // Objective-C method resolver - we need to JIT it.
 	    if (imp == NULL) {
 		imp = GET_CORE()->compile(func);
 	    }
@@ -4881,6 +4885,8 @@
 
 static IMP old_resolveClassMethod_imp = NULL;
 static IMP old_resolveInstanceMethod_imp = NULL;
+static SEL sel_resolveClassMethod = 0;
+static SEL sel_resolveInstanceMethod = 0;
 
 static BOOL
 resolveClassMethod_imp(void *self, SEL sel, SEL name)
@@ -4900,6 +4906,23 @@
     return NO; // TODO call old IMP
 }
 
+static bool
+class_has_custom_resolver(Class klass)
+{
+    if (!class_isMetaClass(klass)) {
+	klass = *(Class *)klass;
+    }
+    if (class_getMethodImplementation(klass, sel_resolveClassMethod)
+	    != (IMP)resolveClassMethod_imp) {
+	return true;
+    }
+    if (class_getMethodImplementation(klass, sel_resolveInstanceMethod)
+	    != (IMP)resolveInstanceMethod_imp) {
+	return true;
+    }
+    return false;
+}
+
 // We can't trust LLVM to pick the right target at runtime.
 #if __LP64__
 # define TARGET_TRIPLE "x86_64-apple-darwin"
@@ -4929,16 +4952,16 @@
 
     setup_builtin_stubs();
 
+    Class ns_object = (Class)objc_getClass("NSObject");
     Method m;
-    Class ns_object = (Class)objc_getClass("NSObject");
-    m = class_getInstanceMethod(*(Class *)ns_object,
-	sel_registerName("resolveClassMethod:"));
+    sel_resolveClassMethod = sel_registerName("resolveClassMethod:");
+    m = class_getInstanceMethod(*(Class *)ns_object, sel_resolveClassMethod);
     assert(m != NULL);
     old_resolveClassMethod_imp = method_getImplementation(m);
     method_setImplementation(m, (IMP)resolveClassMethod_imp);
 
-    m = class_getInstanceMethod(*(Class *)ns_object,
-	sel_registerName("resolveInstanceMethod:"));
+    sel_resolveInstanceMethod = sel_registerName("resolveInstanceMethod:");
+    m = class_getInstanceMethod(*(Class *)ns_object, sel_resolveInstanceMethod);
     assert(m != NULL);
     old_resolveInstanceMethod_imp = method_getImplementation(m);
     method_setImplementation(m, (IMP)resolveInstanceMethod_imp);
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.macosforge.org/pipermail/macruby-changes/attachments/20100418/6522ebf9/attachment.html>


More information about the macruby-changes mailing list