Skip to content

Instantly share code, notes, and snippets.

@TheDreamsWind
Last active November 23, 2022 21:02
Show Gist options
  • Save TheDreamsWind/20e353216a61cfaf82185a93135cc6e1 to your computer and use it in GitHub Desktop.
Save TheDreamsWind/20e353216a61cfaf82185a93135cc6e1 to your computer and use it in GitHub Desktop.
[SO-a/73343830/5690248] An example of lazily named class
//
// main.m
// ObjCPlayground
//
// Created by Aleksandr Medvedev on 04.08.2022.
//
#include <objc/runtime.h>
#include <stdio.h>
@import Foundation;
#pragma mark - Class Layout
struct LazyNameClassLayout {
struct LazyNameClassLayout *isa;
struct LazyNameClassLayout *superclass;
void *cachePtr;
uintptr_t zero;
uintptr_t roSection;
};
struct LazyNameClassLayoutRO {
} LazyNameMetaclassRO;
#pragma mark - Meta Class
#pragma mark Magic Stuff from runtime
extern struct objc_cache _objc_empty_cache;
extern struct LazyNameClassLayout OBJC_METACLASS_$_NSObject;
extern struct LazyNameClassLayout OBJC_CLASS_$_NSObject;
struct LazyNameClassLayout LazyNameMetaclass = {
.isa = &OBJC_METACLASS_$_NSObject,
.superclass = &OBJC_METACLASS_$_NSObject,
.cachePtr = &_objc_empty_cache,
.roSection = (uintptr_t)&LazyNameMetaclassRO,
};
#pragma mark - Concrete Class
struct LazyNameClassLayoutRO LazyNameClassRO = {};
struct LazyNameClassLayout LazyNameClass = {
.isa = &LazyNameMetaclass,
.superclass = Nil,
.cachePtr = &_objc_empty_cache,
.roSection = (uintptr_t)&LazyNameClassRO,
};
#pragma mark - Namer
static objc_hook_lazyClassNamer OrigNamer;
static const char *ClassNamer(Class cls) {
if (cls == (__bridge Class)(&LazyNameClass)) {
return "Lazy Name";
}
return OrigNamer(cls);
}
#pragma mark - Main
int main(int argc, const char * argv[]) {
objc_setHook_lazyClassNamer(ClassNamer, &OrigNamer);
printf("%s\n", class_getName([(__bridge Class)&LazyNameClass class]));
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment