getImageNameHook.m [plain text]
// TEST_CONFIG
#include "test.h"
#include "testroot.i"
@interface One : TestRoot @end
@implementation One @end
@interface Two : TestRoot @end
@implementation Two @end
@interface Both : TestRoot @end
@implementation Both @end
@interface None : TestRoot @end
@implementation None @end
objc_hook_getImageName OnePreviousHook;
BOOL GetImageNameHookOne(Class cls, const char **outName)
{
if (0 == strcmp(class_getName(cls), "One")) {
*outName = "Image One";
return YES;
} else if (0 == strcmp(class_getName(cls), "Both")) {
*outName = "Image Both via One";
return YES;
} else {
return OnePreviousHook(cls, outName);
}
}
objc_hook_getImageName TwoPreviousHook;
BOOL GetImageNameHookTwo(Class cls, const char **outName)
{
if (0 == strcmp(class_getName(cls), "Two")) {
*outName = "Image Two";
return YES;
} else if (0 == strcmp(class_getName(cls), "Both")) {
*outName = "Image Both via Two";
return YES;
} else {
return TwoPreviousHook(cls, outName);
}
}
int main()
{
// before hooks: main executable is the image name for four classes
testassert(strstr(class_getImageName([One class]), "getImageNameHook"));
testassert(strstr(class_getImageName([Two class]), "getImageNameHook"));
testassert(strstr(class_getImageName([Both class]), "getImageNameHook"));
testassert(strstr(class_getImageName([None class]), "getImageNameHook"));
testassert(strstr(class_getImageName([NSObject class]), "libobjc"));
// install hook One
objc_setHook_getImageName(GetImageNameHookOne, &OnePreviousHook);
// two classes are in Image One with hook One in place
testassert(strstr(class_getImageName([One class]), "Image One"));
testassert(strstr(class_getImageName([Two class]), "getImageNameHook"));
testassert(strstr(class_getImageName([Both class]), "Image Both via One"));
testassert(strstr(class_getImageName([None class]), "getImageNameHook"));
testassert(strstr(class_getImageName([NSObject class]), "libobjc"));
// install hook Two which chains to One
objc_setHook_getImageName(GetImageNameHookTwo, &TwoPreviousHook);
// two classes are in Image Two and one in One with both hooks in place
testassert(strstr(class_getImageName([One class]), "Image One"));
testassert(strstr(class_getImageName([Two class]), "Image Two"));
testassert(strstr(class_getImageName([Both class]), "Image Both via Two"));
testassert(strstr(class_getImageName([None class]), "getImageNameHook"));
testassert(strstr(class_getImageName([NSObject class]), "libobjc"));
succeed(__FILE__);
}