Fix invoking missing superclass methods.

The lookup functions for the superclass paths were silently ignoring
missing methods, rather than calling the forwarding hook.

Fixes #153
main
David Chisnall 6 years ago committed by David Chisnall
parent fa2914b13c
commit 78ff24516c

@ -36,6 +36,7 @@ set(TESTS
ProtocolCreation.m
ResurrectInDealloc_arc.m
RuntimeTest.m
SuperMethodMissing.m
WeakBlock_arc.m
WeakRefLoad.m
WeakReferences_arc.m

@ -0,0 +1,46 @@
#include "Test.h"
#include "objc/hooks.h"
#include <stdio.h>
@interface Test (DoesNotExist)
- (void)run;
@end
@interface Foo : Test
@end
@implementation Foo
- (void)run
{
[super run];
}
@end
static int missing_methods;
id forward(id self, SEL cmd, ...)
{
Class cls = object_getClass(self);
missing_methods++;
fprintf(stderr, "Missing method: %c[%s %s]\n", class_isMetaClass(cls) ? '+' : '-', class_getName(cls),sel_getName(cmd));
return nil;
}
IMP no_method(id self, SEL cmd)
{
return forward;
}
int
main()
{
__objc_msg_forward2 = no_method;
Test *t = [Test new];
[t run];
assert(missing_methods == 1);
Foo *f = [Foo new];
[f run];
assert(missing_methods == 2);
//[Test run];
}

@ -302,7 +302,8 @@ struct objc_slot2 *objc_slot_lookup_super2(struct objc_super *super, SEL selecto
objc_send_initialize((id)class);
return objc_slot_lookup_super2(super, selector);
}
return (struct objc_slot2*)&nil_slot;
uncacheable_slot.imp = __objc_msg_forward2(receiver, selector);
return (struct objc_slot2*)&uncacheable_slot;
}
return result;
}
@ -335,7 +336,11 @@ struct objc_slot *objc_slot_lookup_super(struct objc_super *super, SEL selector)
objc_send_initialize((id)class);
return objc_slot_lookup_super(super, selector);
}
return &nil_slot_v1;
uncacheable_slot_v1.owner = Nil;
uncacheable_slot_v1.types = sel_getType_np(selector);
uncacheable_slot_v1.selector = selector;
uncacheable_slot_v1.method = __objc_msg_forward2(receiver, selector);
return &uncacheable_slot_v1;
}
uncacheable_slot_v1.owner = Nil;
uncacheable_slot_v1.types = sel_getType_np(((struct objc_method*)result)->selector);

Loading…
Cancel
Save