Question

I'm trying to inject my code at runtime to delegate tableView:didSelectRowAtIndexPath:. I have following code:

static void overridingDidSelectCellAtIndexPath(void (^listener)(id _self, UITableView *tableView, NSIndexPath *indexPath)) {

    Method didSelectRowAtIndexPath = class_getInstanceMethod([ViewController class], @selector(tableView:didSelectRowAtIndexPath:));
    IMP originalImp = method_getImplementation(didSelectRowAtIndexPath);

    void (^bl)(id, UITableView *, NSIndexPath *) = ^(id _self, UITableView *tableView, NSIndexPath *indexPath) {

        originalImp(_self, @selector(tableView:didSelectRowAtIndexPath:), tableView, indexPath);
        listener(_self, tableView, indexPath);
    };

    IMP newImp = imp_implementationWithBlock((__bridge id)((__bridge void*)bl));
    method_setImplementation(didSelectRowAtIndexPath, newImp);
}

I invoke it in:

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {


    overridingDidSelectCellAtIndexPath(^(id _self, UITableView *tableView, NSIndexPath *indexPath) {

        UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];
        [cell.textLabel setText:@"Hello"];
    });

    return [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
}

Line which causes crash:

originalImp(_self, @selector(tableView:didSelectRowAtIndexPath:), tableView, indexPath);

I get no exception, my backtrace from lldb:

* thread #1: tid = 0x75249, 0x37b9b0f8 libobjc.A.dylib`objc_retain + 8, queue = 
'com.apple.main-thread, stop reason = EXC_BAD_ACCESS (code=1, address=0x8)

frame #0: 0x37b9b0f8 libobjc.A.dylib`objc_retain + 8

frame #1: 0x0000aab0 
GetAllMethods`__overridingDidSelectCellAtIndexPath_block_invoke(.block_descriptor=0x14d49870, _self=0x14d48690, tableView=0x15121400, indexPath=0x14d51870) + 120 at ViewController.m:68

frame #2: 0x300e30ca UIKit`-[UITableView _selectRowAtIndexPath:animated:scrollPosition:notifyDelegate:] + 1078

frame #3: 0x30196862 UIKit`-[UITableView _userSelectRowAtPendingSelectionIndexPath:] + 214

frame #4: 0x30046780 UIKit`_applyBlockToCFArrayCopiedToStack + 316

frame #5: 0x2ffbe7ba UIKit`_afterCACommitHandler + 430

frame #6: 0x2d80cf68 CoreFoundation`__CFRUNLOOP_IS_CALLING_OUT_TO_AN_OBSERVER_CALLBACK_FUNCTION__ + 20

frame #7: 0x2d80a8f6 CoreFoundation`__CFRunLoopDoObservers + 286

frame #8: 0x2d80ac42 CoreFoundation`__CFRunLoopRun + 738

frame #9: 0x2d775470 CoreFoundation`CFRunLoopRunSpecific + 524

frame #10: 0x2d775252 CoreFoundation`CFRunLoopRunInMode + 106

frame #11: 0x324af2ea GraphicsServices`GSEventRunModal + 138

frame #12: 0x3002a844 UIKit`UIApplicationMain + 1136

frame #13: 0x0000b080 GetAllMethods`main(argc=1, argv=0x27dfecdc) + 116 at main.m:16

No correct solution

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top