aboutsummaryrefslogtreecommitdiffstats
path: root/gcc-4.4.3/libobjc/Protocol.m
diff options
context:
space:
mode:
authorJing Yu <jingyu@google.com>2010-07-22 14:03:48 -0700
committerJing Yu <jingyu@google.com>2010-07-22 14:03:48 -0700
commitb094d6c4bf572654a031ecc4afe675154c886dc5 (patch)
tree89394c56b05e13a5413ee60237d65b0214fd98e2 /gcc-4.4.3/libobjc/Protocol.m
parentdc34721ac3bf7e3c406fba8cfe9d139393345ec5 (diff)
downloadtoolchain_gcc-b094d6c4bf572654a031ecc4afe675154c886dc5.tar.gz
toolchain_gcc-b094d6c4bf572654a031ecc4afe675154c886dc5.tar.bz2
toolchain_gcc-b094d6c4bf572654a031ecc4afe675154c886dc5.zip
commit gcc-4.4.3 which is used to build gcc-4.4.3 Android toolchain in master.
The source is based on fsf gcc-4.4.3 and contains local patches which are recorded in gcc-4.4.3/README.google. Change-Id: Id8c6d6927df274ae9749196a1cc24dbd9abc9887
Diffstat (limited to 'gcc-4.4.3/libobjc/Protocol.m')
-rw-r--r--gcc-4.4.3/libobjc/Protocol.m180
1 files changed, 180 insertions, 0 deletions
diff --git a/gcc-4.4.3/libobjc/Protocol.m b/gcc-4.4.3/libobjc/Protocol.m
new file mode 100644
index 000000000..9fa7f9258
--- /dev/null
+++ b/gcc-4.4.3/libobjc/Protocol.m
@@ -0,0 +1,180 @@
+/* This file contains the implementation of class Protocol.
+ Copyright (C) 1993, 2004, 2009 Free Software Foundation, Inc.
+
+This file is part of GCC.
+
+GCC is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 3, or (at your option)
+any later version.
+
+GCC is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+Under Section 7 of GPL version 3, you are granted additional
+permissions described in the GCC Runtime Library Exception, version
+3.1, as published by the Free Software Foundation.
+
+You should have received a copy of the GNU General Public License and
+a copy of the GCC Runtime Library Exception along with this program;
+see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
+<http://www.gnu.org/licenses/>. */
+
+#include "objc/Protocol.h"
+#include "objc/objc-api.h"
+
+/* Method description list */
+struct objc_method_description_list {
+ int count;
+ struct objc_method_description list[1];
+};
+
+
+@implementation Protocol
+{
+@private
+ char *protocol_name;
+ struct objc_protocol_list *protocol_list;
+ struct objc_method_description_list *instance_methods, *class_methods;
+}
+
+/* Obtaining attributes intrinsic to the protocol */
+
+- (const char *)name
+{
+ return protocol_name;
+}
+
+/* Testing protocol conformance */
+
+- (BOOL) conformsTo: (Protocol *)aProtocolObject
+{
+ size_t i;
+ struct objc_protocol_list* proto_list;
+
+ if (aProtocolObject == nil)
+ return NO;
+
+ if (!strcmp(aProtocolObject->protocol_name, self->protocol_name))
+ return YES;
+
+ for (proto_list = protocol_list; proto_list; proto_list = proto_list->next)
+ {
+ for (i=0; i < proto_list->count; i++)
+ {
+ if ([proto_list->list[i] conformsTo: aProtocolObject])
+ return YES;
+ }
+ }
+
+ return NO;
+}
+
+/* Looking up information specific to a protocol */
+
+- (struct objc_method_description *) descriptionForInstanceMethod:(SEL)aSel
+{
+ int i;
+ struct objc_protocol_list* proto_list;
+ const char* name = sel_get_name (aSel);
+ struct objc_method_description *result;
+
+ if (instance_methods)
+ for (i = 0; i < instance_methods->count; i++)
+ {
+ if (!strcmp ((char*)instance_methods->list[i].name, name))
+ return &(instance_methods->list[i]);
+ }
+
+ for (proto_list = protocol_list; proto_list; proto_list = proto_list->next)
+ {
+ size_t j;
+ for (j=0; j < proto_list->count; j++)
+ {
+ if ((result = [proto_list->list[j]
+ descriptionForInstanceMethod: aSel]))
+ return result;
+ }
+ }
+
+ return NULL;
+}
+
+- (struct objc_method_description *) descriptionForClassMethod:(SEL)aSel;
+{
+ int i;
+ struct objc_protocol_list* proto_list;
+ const char* name = sel_get_name (aSel);
+ struct objc_method_description *result;
+
+ if (class_methods)
+ for (i = 0; i < class_methods->count; i++)
+ {
+ if (!strcmp ((char*)class_methods->list[i].name, name))
+ return &(class_methods->list[i]);
+ }
+
+ for (proto_list = protocol_list; proto_list; proto_list = proto_list->next)
+ {
+ size_t j;
+ for (j=0; j < proto_list->count; j++)
+ {
+ if ((result = [proto_list->list[j]
+ descriptionForClassMethod: aSel]))
+ return result;
+ }
+ }
+
+ return NULL;
+}
+
+- (unsigned) hash
+{
+ /* Compute a hash of the protocol_name; use the same hash algorithm
+ * that we use for class names; protocol names and class names are
+ * somewhat similar types of string spaces.
+ */
+ int hash = 0, index;
+
+ for (index = 0; protocol_name[index] != '\0'; index++)
+ {
+ hash = (hash << 4) ^ (hash >> 28) ^ protocol_name[index];
+ }
+
+ hash = (hash ^ (hash >> 10) ^ (hash >> 20));
+
+ return hash;
+}
+
+/*
+ * Equality between formal protocols is only formal (nothing to do
+ * with actually checking the list of methods they have!). Two formal
+ * Protocols are equal if and only if they have the same name.
+ *
+ * Please note (for comparisons with other implementations) that
+ * checking the names is equivalent to checking that Protocol A
+ * conforms to Protocol B and Protocol B conforms to Protocol A,
+ * because this happens iff they have the same name. If they have
+ * different names, A conforms to B if and only if A includes B, but
+ * the situation where A includes B and B includes A is a circular
+ * dependency between Protocols which is forbidden by the compiler, so
+ * A conforms to B and B conforms to A with A and B having different
+ * names is an impossible case.
+ */
+- (BOOL) isEqual: (id)obj
+{
+ if (obj == self)
+ return YES;
+
+ if ([obj isKindOf: [Protocol class]])
+ {
+ if (strcmp (protocol_name, ((Protocol *)obj)->protocol_name) == 0)
+ return YES;
+ }
+
+ return NO;
+}
+@end
+