Ta android + ios

This commit is contained in:
LYP
2024-08-07 20:22:28 +08:00
parent 69fee08c61
commit 76458664d8
722 changed files with 41709 additions and 1 deletions

View File

@@ -0,0 +1,14 @@
#import <Foundation/Foundation.h>
NS_ASSUME_NONNULL_BEGIN
@interface NSObject (TDNewSwizzle)
+ (BOOL)td_new_swizzleMethod:(SEL)origSel_ withMethod:(SEL)altSel_ error:(NSError **)error_;
+ (BOOL)td_new_swizzleClassMethod:(SEL)origSel_ withClassMethod:(SEL)altSel_ error:(NSError **)error_;
+ (BOOL)td_new_swizzleMethod:(SEL)origSel_ withClass:(Class)altCla_ withMethod:(SEL)altSel_ error:(NSError **)error_;
@end
NS_ASSUME_NONNULL_END

View File

@@ -0,0 +1,33 @@
fileFormatVersion: 2
guid: f13e46f9ceae76041a668ce21ee63c12
PluginImporter:
externalObjects: {}
serializedVersion: 2
iconMap: {}
executionOrder: {}
defineConstraints: []
isPreloaded: 0
isOverridable: 0
isExplicitlyReferenced: 0
validateReferences: 1
platformData:
- first:
Any:
second:
enabled: 0
settings: {}
- first:
Editor: Editor
second:
enabled: 0
settings:
DefaultValueInitialized: true
- first:
iPhone: iOS
second:
enabled: 1
settings:
AddToEmbeddedBinaries: false
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,155 @@
#import "TDNewSwizzle.h"
#if TARGET_OS_IOS
#import <objc/runtime.h>
#import <objc/message.h>
#else
#import <objc/objc-class.h>
#endif
#define TDSetNSErrorFor(FUNC, ERROR_VAR, FORMAT,...) \
if (ERROR_VAR) { \
NSString *errStr = [NSString stringWithFormat:@"%s: " FORMAT,FUNC,##__VA_ARGS__]; \
*ERROR_VAR = [NSError errorWithDomain:@"NSCocoaErrorDomain" \
code:-1 \
userInfo:[NSDictionary dictionaryWithObject:errStr forKey:NSLocalizedDescriptionKey]]; \
}
#define TDSetNSError(ERROR_VAR, FORMAT,...) TDSetNSErrorFor(__func__, ERROR_VAR, FORMAT, ##__VA_ARGS__)
#if OBJC_API_VERSION >= 2
#define TDGetClass(obj) object_getClass(obj)
#else
#define TDGetClass(obj) (obj ? obj->isa : Nil)
#endif
@implementation NSObject (TDNewSwizzle)
+ (BOOL)td_new_swizzleMethod:(SEL)origSel_ withClass:(Class)altCla_ withMethod:(SEL)altSel_ error:(NSError **)error_ {
Method origMethod = class_getInstanceMethod(self, origSel_);
if (!origMethod) {
TDSetNSError(error_, @"original method %@ not found for class %@", NSStringFromSelector(origSel_), [self class]);
return NO;
}
Method altMethod = class_getInstanceMethod(altCla_, altSel_);
if (!altMethod) {
TDSetNSError(error_, @"alternate method %@ not found for class %@", NSStringFromSelector(altSel_), [altCla_ class]);
return NO;
}
class_addMethod(self,
origSel_,
class_getMethodImplementation(self, origSel_),
method_getTypeEncoding(origMethod));
class_addMethod(altCla_,
altSel_,
class_getMethodImplementation(altCla_, altSel_),
method_getTypeEncoding(altMethod));
//
BOOL didAddMethod = class_addMethod(self,
altSel_,
method_getImplementation(altMethod),
method_getTypeEncoding(altMethod));
if (didAddMethod) {
method_exchangeImplementations(origMethod, class_getInstanceMethod(self, altSel_));
}
return didAddMethod;
}
+ (BOOL)td_new_swizzleMethod:(SEL)origSel_ withMethod:(SEL)altSel_ error:(NSError **)error_ {
#if OBJC_API_VERSION >= 2
Method origMethod = class_getInstanceMethod(self, origSel_);
if (!origMethod) {
TDSetNSError(error_, @"original method %@ not found for class %@", NSStringFromSelector(origSel_), [self class]);
return NO;
}
Method altMethod = class_getInstanceMethod(self, altSel_);
if (!altMethod) {
TDSetNSError(error_, @"alternate method %@ not found for class %@", NSStringFromSelector(altSel_), [self class]);
return NO;
}
class_addMethod(self,
origSel_,
class_getMethodImplementation(self, origSel_),
method_getTypeEncoding(origMethod));
class_addMethod(self,
altSel_,
class_getMethodImplementation(self, altSel_),
method_getTypeEncoding(altMethod));
method_exchangeImplementations(class_getInstanceMethod(self, origSel_), class_getInstanceMethod(self, altSel_));
return YES;
#else
// Scan for non-inherited methods.
Method directOriginalMethod = NULL, directAlternateMethod = NULL;
void *iterator = NULL;
struct objc_method_list *mlist = class_nextMethodList(self, &iterator);
while (mlist) {
int method_index = 0;
for (; method_index < mlist->method_count; method_index++) {
if (mlist->method_list[method_index].method_name == origSel_) {
assert(!directOriginalMethod);
directOriginalMethod = &mlist->method_list[method_index];
}
if (mlist->method_list[method_index].method_name == altSel_) {
assert(!directAlternateMethod);
directAlternateMethod = &mlist->method_list[method_index];
}
}
mlist = class_nextMethodList(self, &iterator);
}
// If either method is inherited, copy it up to the target class to make it non-inherited.
if (!directOriginalMethod || !directAlternateMethod) {
Method inheritedOriginalMethod = NULL, inheritedAlternateMethod = NULL;
if (!directOriginalMethod) {
inheritedOriginalMethod = class_getInstanceMethod(self, origSel_);
if (!inheritedOriginalMethod) {
TDSetNSError(error_, @"original method %@ not found for class %@", NSStringFromSelector(origSel_), [self className]);
return NO;
}
}
if (!directAlternateMethod) {
inheritedAlternateMethod = class_getInstanceMethod(self, altSel_);
if (!inheritedAlternateMethod) {
TDSetNSError(error_, @"alternate method %@ not found for class %@", NSStringFromSelector(altSel_), [self className]);
return NO;
}
}
int hoisted_method_count = !directOriginalMethod && !directAlternateMethod ? 2 : 1;
struct objc_method_list *hoisted_method_list = malloc(sizeof(struct objc_method_list) + (sizeof(struct objc_method)*(hoisted_method_count-1)));
hoisted_method_list->obsolete = NULL; // soothe valgrind - apparently ObjC runtime accesses this value and it shows as uninitialized in valgrind
hoisted_method_list->method_count = hoisted_method_count;
Method hoisted_method = hoisted_method_list->method_list;
if (!directOriginalMethod) {
bcopy(inheritedOriginalMethod, hoisted_method, sizeof(struct objc_method));
directOriginalMethod = hoisted_method++;
}
if (!directAlternateMethod) {
bcopy(inheritedAlternateMethod, hoisted_method, sizeof(struct objc_method));
directAlternateMethod = hoisted_method;
}
class_addMethods(self, hoisted_method_list);
}
// Swizzle.
IMP temp = directOriginalMethod->method_imp;
directOriginalMethod->method_imp = directAlternateMethod->method_imp;
directAlternateMethod->method_imp = temp;
return YES;
#endif
}
+ (BOOL)td_new_swizzleClassMethod:(SEL)origSel_ withClassMethod:(SEL)altSel_ error:(NSError **)error_ {
return [TDGetClass((id)self) td_new_swizzleMethod:origSel_ withMethod:altSel_ error:error_];
}
@end

View File

@@ -0,0 +1,33 @@
fileFormatVersion: 2
guid: 83e5e45c60e92754d917ed33e60f7552
PluginImporter:
externalObjects: {}
serializedVersion: 2
iconMap: {}
executionOrder: {}
defineConstraints: []
isPreloaded: 0
isOverridable: 0
isExplicitlyReferenced: 0
validateReferences: 1
platformData:
- first:
Any:
second:
enabled: 0
settings: {}
- first:
Editor: Editor
second:
enabled: 0
settings:
DefaultValueInitialized: true
- first:
iPhone: iOS
second:
enabled: 1
settings:
AddToEmbeddedBinaries: false
userData:
assetBundleName:
assetBundleVariant: