Created
December 1, 2020 12:55
-
-
Save storoj/edd0a664eab6a2f59754795e027a0e35 to your computer and use it in GitHub Desktop.
ObjC Hachik
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#import <objc/runtime.h> | |
#import <objc/message.h> | |
template <typename RET, typename ...Types> | |
class ObjcMethodHook { | |
typedef RET(*_IMP)(id _self, SEL _cmd, Types...); | |
typedef RET(^_IMPBlock)(id _self, Types...); | |
private: | |
Class m_cls; | |
SEL m_sel; | |
_IMP m_orig; | |
public: | |
ObjcMethodHook(Class cls, SEL sel) : m_cls(cls), m_sel(sel), m_orig(NULL) {}; | |
ObjcMethodHook(const char *cls, const char *sel) : ObjcMethodHook(objc_lookUpClass(cls), sel_getUid(sel)) {}; | |
void hook(_IMPBlock imp) { | |
Method m = class_getInstanceMethod(m_cls, m_sel); | |
m = class_getInstanceMethod(m_cls, m_sel); | |
m_orig = (_IMP)class_replaceMethod(m_cls, m_sel, imp_implementationWithBlock(imp), method_getTypeEncoding(m)); | |
}; | |
RET super(id _self, Types... args) { | |
if (m_orig) { | |
return m_orig(_self, m_sel, args...); | |
} else { | |
struct objc_super s = { | |
_self, | |
class_getSuperclass(m_cls) | |
}; | |
return ((_IMP)objc_msgSendSuper)((__bridge id)&s, m_sel, args...); | |
} | |
}; | |
RET call(id _self, Types... args) { | |
return ((_IMP)objc_msgSend)(_self, m_sel, args...); | |
} | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment