Ejemplo n.º 1
0
void objc_update_dtable(Class cls) {
    struct objc_method_list* ml;
    struct objc_category** cats;
    unsigned int i;

    if (!(cls->info & OBJC_CLASS_INFO_DTABLE))
        return;

    if (cls->dtable == empty_dtable)
        cls->dtable = objc_sparsearray_new();

    if (cls->superclass != Nil)
        objc_sparsearray_copy(cls->dtable, cls->superclass->dtable);

    for (ml = cls->methodlist; ml != NULL; ml = ml->next)
        for (i = 0; i < ml->count; i++)
            objc_sparsearray_set(cls->dtable, (uint32_t)ml->methods[i].sel.uid, ml->methods[i].imp);

    if ((cats = objc_categories_for_class(cls)) != NULL) {
        for (i = 0; cats[i] != NULL; i++) {
            unsigned int j;

            ml = (cls->info & OBJC_CLASS_INFO_CLASS ? cats[i]->instance_methods : cats[i]->class_methods);

            for (; ml != NULL; ml = ml->next)
                for (j = 0; j < ml->count; j++)
                    objc_sparsearray_set(cls->dtable, (uint32_t)ml->methods[j].sel.uid, ml->methods[j].imp);
        }
    }

    if (cls->subclass_list != NULL)
        for (i = 0; cls->subclass_list[i] != NULL; i++)
            objc_update_dtable(cls->subclass_list[i]);
}
Ejemplo n.º 2
0
const char* objc_get_type_encoding(Class cls, SEL sel) {
    struct objc_method_list* ml;
    struct objc_category** cats;
    unsigned int i;

    objc_global_mutex_lock();

    for (ml = cls->methodlist; ml != NULL; ml = ml->next) {
        for (i = 0; i < ml->count; i++) {
            if (ml->methods[i].sel.uid == sel->uid) {
                const char* ret = ml->methods[i].sel.types;
                objc_global_mutex_unlock();
                return ret;
            }
        }
    }

    if ((cats = objc_categories_for_class(cls)) != NULL) {
        for (; *cats != NULL; cats++) {
            for (ml = (*cats)->instance_methods; ml != NULL; ml = ml->next) {
                for (i = 0; i < ml->count; i++) {
                    if (ml->methods[i].sel.uid == sel->uid) {
                        const char* ret = ml->methods[i].sel.types;
                        objc_global_mutex_unlock();
                        return ret;
                    }
                }
            }
        }
    }

    objc_global_mutex_unlock();

    return NULL;
}
Ejemplo n.º 3
0
// INVARIANT: This must happen under lock.
IMP _class_lookupMethodImplementation(Class cls, SEL sel, struct objc_method **outMethod) {
	struct objc_method *method = NULL;
	struct objc_method_list *ml;
	struct objc_category **cats;
	unsigned int i;

    for (ml = cls->methodlist; ml != NULL; ml = ml->next)
    {
        for (i = 0; i < ml->count; i++)
        {
            if (ml->methods[i].sel.uid == sel->uid)
            {
                method = &ml->methods[i];
                goto out;
            }
        }
    }

    if ((cats = objc_categories_for_class(cls)) != NULL)
    {
        for (; *cats != NULL; cats++)
        {
            if (cls->info & OBJC_CLASS_INFO_METACLASS)
                ml = (*cats)->class_methods;
            else
                ml = (*cats)->instance_methods;

            for (; ml != NULL; ml = ml->next)
            {
                for (i = 0; i < ml->count; i++)
                {
                    if (ml->methods[i].sel.uid ==
                        sel->uid)
                    {
                        method = &ml->methods[i];
                        goto out;
                    }
                }
            }
        }
    }

out:
	if(method) {
		if(outMethod) {
			*outMethod = method;
		}
		return method->imp;
	}

	return (IMP)nil;
}