[Xfce4-commits] <glib-objc:no-foundation-dep> add compat functions to Object for Objc 2.0 compiles

Brian J. Tarricone noreply at xfce.org
Sun Nov 22 04:02:13 CET 2009


Updating branch refs/heads/no-foundation-dep
         to 74d6eb3048508eab2cd405d9947afcc17db1409f (commit)
       from 1d91dc5a0c829920f3fcace5d9bdf5fdcad4e357 (commit)

commit 74d6eb3048508eab2cd405d9947afcc17db1409f
Author: Brian J. Tarricone <brian at tarricone.org>
Date:   Tue Jul 7 23:35:16 2009 -0700

    add compat functions to Object for Objc 2.0 compiles
    
    i'm not sure if this is actually needed, but it was fun to play with
    the runtime

 glib-objc/GOCObjectBase.h |   32 ++++++++-
 glib-objc/GOCObjectBase.m |  174 +++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 203 insertions(+), 3 deletions(-)

diff --git a/glib-objc/GOCObjectBase.h b/glib-objc/GOCObjectBase.h
index 46a9c06..dfe4e04 100644
--- a/glib-objc/GOCObjectBase.h
+++ b/glib-objc/GOCObjectBase.h
@@ -17,7 +17,6 @@
  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301, USA.
  */
 
-
 #ifndef __GOC_OBJECT_BASE_H__
 #define __GOC_OBJECT_BASE_H__
 
@@ -38,9 +37,36 @@
     volatile int ref_count;
 }
 
-- (id <GOCObject>)ref;
-- (void)unref;
+ at end
+
+#if __OBJC2__
+
+/* ObjC 2.0 doesn't have these methods in Object because apparently Apple decided
+ * everyone in the world should use NSObject */
+
+ at interface Object (ObjC1Compat)
+
+- (id)init;
+
++ (id)new;
++ (id)alloc;
+- (void)free;
+
+- (Class)class;
+- (Class)superClass;
+- (const char *)name;
+
+- (BOOL)isKindOfClass:(Class)aClass;
+- (BOOL)isMemberOfClass:(Class)aClass;
+
+- (BOOL)respondsTo:(SEL)aSel;
+- (BOOL)conformsTo:(Protocol *)aProtocol;
+
++ (IMP)instanceMethodFor:(SEL)aSel;
+- (IMP)methodFor:(SEL)aSel;
 
 @end
 
+#endif  /* __OBJC2__ */
+
 #endif  /* __GOC_OBJECT_BASE_H__ */
diff --git a/glib-objc/GOCObjectBase.m b/glib-objc/GOCObjectBase.m
index bbe1210..1ace1a9 100644
--- a/glib-objc/GOCObjectBase.m
+++ b/glib-objc/GOCObjectBase.m
@@ -21,6 +21,16 @@
 #include <config.h>
 #endif
 
+#if __OBJC2__
+# if defined(__NEXT_RUNTIME__)
+#  include <objc/objc-runtime.h>
+# elif defined(__GNUC__)
+#  include <objc/objc-api.h>
+# else
+#  error "We don't support your ObjC runtime!"
+# endif
+#endif
+
 #include <glib.h>
 
 #import "GOCObjectBase.h"
@@ -63,3 +73,167 @@
 }
 
 @end
+
+
+#if __OBJC2__
+
+ at implementation Object (ObjC1Compat)
+
+- (id)init
+{
+    return self;
+}
+
++ (id)new
+{
+    return [[self alloc] init];
+}
+
++ (id)alloc
+{
+#if defined(__NEXT_RUNTIME__)
+    return class_createInstance([self class], 0);
+#elif defined(__GNUC__)
+    return class_create_instance([self class]);
+#endif
+}
+
+- (void)free
+{
+    object_dispose(self);
+}
+
+- (Class)class
+{
+#if defined(__NEXT_RUNTIME__)
+    return object_getClass(self);
+#elif defined(__GNUC__)
+    return object_get_class(self);
+#endif
+}
+- (Class)superClass
+{
+#if defined(__NEXT_RUNTIME__)
+    return class_getSuperclass([self class]);
+#elif defined(__GNUC__)
+    return object_get_super_class(self);
+#endif
+}
+
+- (const char *)name
+{
+#if defined(__NEXT_RUNTIME__)
+    return object_getClassName(self);
+#elif defined(__GNUC__)
+    return object_get_class_name(self);
+#endif
+}
+
+- (BOOL)isKindOfClass:(Class)aClass
+{
+    Class cur = aClass;
+    Class ourClass = [self class];
+
+    while(cur) {
+        if(ourClass == cur)
+            return YES;
+#if defined(__NEXT_RUNTIME__)
+        cur = class_getSuperclass(cur);
+#elif defined(__GNUC__)
+        cur = class_get_super_class(cur);
+#endif
+    }
+
+    return NO;
+}
+
+- (BOOL)isMemberOfClass:(Class)aClass
+{
+    return [self class] == aClass ? YES : NO;
+}
+
+- (BOOL)respondsTo:(SEL)aSel
+{
+#if defined(__NEXT_RUNTIME__)
+    return class_respondsToSelector([self class], aSel);
+#elif defined(__GNUC__)
+    return class_get_instance_method([self class], aSel) ? YES : NO;
+#endif
+}
+
+- (BOOL)conformsTo:(Protocol *)aProtocol
+{
+#if defined(__NEXT_RUNTIME__)
+    return class_conformsToProtocol([self class], aProtocol);
+#elif defined(__GNUC__)
+    struct objc_class *cl = (struct objc_class *)[self class];
+    struct objc_protocol_list *pl;
+    size_t i;
+
+    for(pl = cl->protocols; pl; pl = pl->next) {
+        for(i = 0; i < pl->count; ++i) {
+            if(pl->list[i] == aProtocol)
+                return YES;
+        }
+    }
+
+    return NO;
+#endif
+}
+
+static IMP
+try_get_instance_method(Class aClass,
+                        SEL aSel)
+{
+    IMP impl = NULL;
+
+#if defined(__NEXT_RUNTIME__)
+    Method method = class_getInstanceMethod(aClass, aSel);
+    if(method)
+        impl = method_getImplementation(method);
+#elif defined(__GNUC__)
+    Method_t method = class_get_instance_method(aClass, aSel);
+    if(method)
+        impl = method_get_imp(method);
+#endif
+
+    return impl;
+}
+
++ (IMP)instanceMethodFor:(SEL)aSel
+{
+    IMP impl = NULL;
+
+#if defined(__NEXT_RUNTIME__)
+    impl = class_getMethodImplementation(self, aSel);
+    if(!impl)
+        impl = class_getMethodImplementation_stret(self, aSel);
+    if(!impl)
+        impl = try_get_instance_method(self, aSel);
+#elif defined(__GNUC__)
+    impl = try_get_instance_method(self, aSel);
+    if(!impl)
+        impl = get_imp(self, aSel);
+#endif
+
+    return impl;
+}
+
+- (IMP)methodFor:(SEL)aSel
+{
+    IMP impl = NULL;
+
+#if defined(__NEXT_RUNTIME__)
+    impl = [[self class] instanceMethodFor:aSel];
+#elif defined(__GNUC__)
+    impl = try_get_instance_method([self class], aSel);
+    if(!impl)
+        impl = objc_msg_lookup(self, aSel);
+#endif
+
+    return impl;
+}
+
+ at end
+
+#endif  /* __OBJC2__ */



More information about the Xfce4-commits mailing list