首次提交

This commit is contained in:
启星
2025-08-08 11:05:33 +08:00
parent 1b3bb91b4a
commit adc1a2a25d
8803 changed files with 708874 additions and 0 deletions

View File

@@ -0,0 +1,39 @@
/*
The MIT License (MIT)
Copyright (c) 2015 Youmi Technology
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
*/
//
// XYDeviceInfoUUID.h
// XYUUID
//
// Created by steve on 2016/7/21.
// Copyright © 2020 guojunliu.github.io. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface XYDeviceInfoUUID : NSObject
+ (NSString *)createDeviceInfoUUID;
@end

View File

@@ -0,0 +1,183 @@
//
// XYDeviceInfoUUID.m
// XYUUID
//
// Created by steve on 2016/7/21.
// Copyright © 2020 guojunliu.github.io. All rights reserved.
//
#import <UIKit/UIKit.h>
#import "XYDeviceInfoUUID.h"
#import <sys/sysctl.h>
#import <CommonCrypto/CommonDigest.h>
#import <CoreTelephony/CTCarrier.h>
#import <CoreTelephony/CTTelephonyNetworkInfo.h>
@implementation XYDeviceInfoUUID
static NSString *systemBootTime(){
struct timeval boottime;
size_t len = sizeof(boottime);
int mib[2] = { CTL_KERN, KERN_BOOTTIME };
if( sysctl(mib, 2, &boottime, &len, NULL, 0) < 0 )
{
return @"";
}
time_t bsec = boottime.tv_sec / 10000;
// time_t bsec = 1476249507 / 10000; // 2016/10/11 13:18:27
// time_t bsec = 1476249507 / 10000; // 2015/10/11 13:18:27
NSString *bootTime = [NSString stringWithFormat:@"%ld",bsec];
return bootTime;
}
static NSString *countryCode() {
NSLocale *locale = [NSLocale currentLocale];
NSString *countryCode = [locale objectForKey:NSLocaleCountryCode];
return countryCode;
}
static NSString *language() {
NSString *language;
NSLocale *locale = [NSLocale currentLocale];
if ([[NSLocale preferredLanguages] count] > 0) {
language = [[NSLocale preferredLanguages]objectAtIndex:0];
} else {
language = [locale objectForKey:NSLocaleLanguageCode];
}
return language;
}
static NSString *systemVersion() {
return [[UIDevice currentDevice] systemVersion];
}
static NSString *deviceName(){
return [[UIDevice currentDevice] name];
}
static const char *SIDFAModel = "hw.model";
static const char *SIDFAMachine = "hw.machine";
static NSString *getSystemHardwareByName(const char *typeSpecifier) {
size_t size;
sysctlbyname(typeSpecifier, NULL, &size, NULL, 0);
char *answer = malloc(size);
sysctlbyname(typeSpecifier, answer, &size, NULL, 0);
NSString *results = [NSString stringWithUTF8String:answer];
free(answer);
return results;
}
static NSUInteger getSysInfo(uint typeSpecifier) {
size_t size = sizeof(int);
int results;
int mib[2] = {CTL_HW, typeSpecifier};
sysctl(mib, 2, &results, &size, NULL, 0);
return (NSUInteger) results;
}
static NSString *carrierInfo() {
NSMutableString* cInfo = [NSMutableString string];
CTTelephonyNetworkInfo *networkInfo = [[CTTelephonyNetworkInfo alloc] init];
CTCarrier *carrier = [networkInfo subscriberCellularProvider];
NSString *carrierName = [carrier carrierName];
if (carrierName != nil){
[cInfo appendString:carrierName];
}
NSString *mcc = [carrier mobileCountryCode];
if (mcc != nil){
[cInfo appendString:mcc];
}
NSString *mnc = [carrier mobileNetworkCode];
if (mnc != nil){
[cInfo appendString:mnc];
}
return cInfo;
}
static NSString *systemHardwareInfo(){
NSString *model = getSystemHardwareByName(SIDFAModel);
NSString *machine = getSystemHardwareByName(SIDFAMachine);
NSString *carInfo = carrierInfo();
NSUInteger totalMemory = getSysInfo(HW_PHYSMEM);
return [NSString stringWithFormat:@"%@,%@,%@,%td",model,machine,carInfo,totalMemory];
}
static NSString *systemFileTime(){
NSFileManager *file = [NSFileManager defaultManager];
NSDictionary *dic= [file attributesOfItemAtPath:@"System/Library/CoreServices" error:nil];
return [NSString stringWithFormat:@"%@,%@",[dic objectForKey:NSFileCreationDate],[dic objectForKey:NSFileModificationDate]];
}
static NSString *disk(){
NSDictionary *fattributes = [[NSFileManager defaultManager] attributesOfFileSystemForPath:NSHomeDirectory() error:nil];
NSString *diskSize = [[fattributes objectForKey:NSFileSystemSize] stringValue];
return diskSize;
}
static void MD5_16(NSString *source, unsigned char *ret){
const char* str = [source UTF8String];
unsigned char result[CC_MD5_DIGEST_LENGTH];
CC_MD5(str, (CC_LONG)strlen(str), result);
for(int i = 4; i < CC_MD5_DIGEST_LENGTH - 4; i++) {
ret[i-4] = result[i];
}
}
static NSString *combineTwoFingerPrint(unsigned char *fp1,unsigned char *fp2){
NSMutableString *hash = [NSMutableString stringWithCapacity:36];
for(int i = 0; i<CC_MD5_DIGEST_LENGTH; i+=1)
{
if (i==4 || i== 6 || i==8 || i==10)
[hash appendString:@"-"];
if (i < 8) {
[hash appendFormat:@"%02X",fp1[i]];
}else{
[hash appendFormat:@"%02X",fp2[i-8]];
}
}
return hash;
}
+ (NSString *)createDeviceInfoUUID {
NSString *sysBootTime = systemBootTime();
NSString *countryC= countryCode();
NSString *languge = language();
NSString *deviceN = deviceName();
NSString *sysVer = systemVersion();
NSString *systemHardware = systemHardwareInfo();
NSString *systemFT = systemFileTime();
NSString *diskS = disk();
NSString *fingerPrintUnstablePart = [NSString stringWithFormat:@"%@,%@,%@,%@", sysBootTime, countryC, languge, deviceN];
NSString *fingerPrintStablePart = [NSString stringWithFormat:@"%@,%@,%@,%@", sysVer, systemHardware, systemFT, diskS];
unsigned char fingerPrintUnstablePartMD5[CC_MD5_DIGEST_LENGTH/2];
MD5_16(fingerPrintUnstablePart,fingerPrintUnstablePartMD5);
unsigned char fingerPrintStablePartMD5[CC_MD5_DIGEST_LENGTH/2];
MD5_16(fingerPrintStablePart,fingerPrintStablePartMD5);
NSString *simulateIDFA = combineTwoFingerPrint(fingerPrintStablePartMD5,fingerPrintUnstablePartMD5);
return simulateIDFA;
}
@end

View File

@@ -0,0 +1,19 @@
//
// XYKeyChain.h
// XYUUID
//
// Created by steve on 2016/7/21.
// Copyright © 2020 guojunliu.github.io. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface XYKeyChain : NSObject
+ (BOOL)setData:(id)data serviceDomain:(NSString *)serviceDomain;
+ (id)getDataWithServiceDomain:(NSString *)serviceDomain;
+ (BOOL)deleteDataWithServiceDomain:(NSString *)serviceDomain;
@end

View File

@@ -0,0 +1,71 @@
//
// XYKeyChain.m
// XYUUID
//
// Created by steve on 2016/7/21.
// Copyright © 2020 guojunliu.github.io. All rights reserved.
//
#import "XYKeyChain.h"
#import <Security/Security.h>
@implementation XYKeyChain
+ (NSMutableDictionary *)getKeychainQueryMap:(NSString *)serviceDomain {
NSMutableDictionary *queryMap = [[NSMutableDictionary alloc] init];
[queryMap setObject:serviceDomain forKey:(__bridge id<NSCopying>)kSecAttrAccount];
[queryMap setObject:serviceDomain forKey:(__bridge id<NSCopying>)kSecAttrService];
[queryMap setObject:(__bridge id)(kSecClassGenericPassword) forKey:(__bridge id<NSCopying>)kSecClass];
[queryMap setObject:(__bridge id)kSecAttrAccessibleAfterFirstUnlock forKey:(__bridge id<NSCopying>)kSecAttrAccessible];
return queryMap;
}
+ (BOOL)setData:(id)data serviceDomain:(NSString *)serviceDomain {
NSMutableDictionary *queryMap = [self getKeychainQueryMap:serviceDomain];
SecItemDelete((__bridge CFDictionaryRef)(queryMap));
NSData *archivedData;
if (@available(iOS 13.0, macOS 13.0, *)) {
NSError *error;
archivedData = [NSKeyedArchiver archivedDataWithRootObject:data requiringSecureCoding:YES error:&error];
if (error) {
return NO;
}
}
else {
archivedData = [NSKeyedArchiver archivedDataWithRootObject:data];
}
[queryMap setObject:archivedData forKey:(__bridge id<NSCopying>)(kSecValueData)];
OSStatus status = SecItemAdd((__bridge CFDictionaryRef)(queryMap), NULL);
return status == errSecSuccess?YES:NO;
}
+ (id)getDataWithServiceDomain:(NSString *)serviceDomain {
id data = nil;
NSMutableDictionary *queryMap = [self getKeychainQueryMap:serviceDomain];
[queryMap setObject:(id)kCFBooleanTrue forKey:(__bridge id<NSCopying>)(kSecReturnData)];
[queryMap setObject:(__bridge id)(kSecMatchLimitOne) forKey:(__bridge id<NSCopying>)(kSecMatchLimit)];
CFTypeRef result = NULL;
CFDictionaryRef cfDicRef = (__bridge_retained CFDictionaryRef)queryMap;
if (SecItemCopyMatching(cfDicRef, &result) == noErr) {
if (@available(iOS 13.0, *)) {
NSError *error;
data = [NSKeyedUnarchiver unarchivedObjectOfClass:[NSString class] fromData:(__bridge NSData*)result error:&error];
}
else {
data = [NSKeyedUnarchiver unarchiveObjectWithData:(__bridge NSData*)result];
}
CFRelease(result);
}
return data;
}
+ (BOOL)deleteDataWithServiceDomain:(NSString *)serviceDomain {
NSMutableDictionary *queryMap = [self getKeychainQueryMap:serviceDomain];
OSStatus status = SecItemDelete((__bridge CFDictionaryRef)(queryMap));
return status == errSecSuccess?YES:NO;
}
@end

View File

@@ -0,0 +1,39 @@
//
// XYUUID.h
// XYUUID
//
// Created by steve on 2016/7/21.
// Copyright © 2020 guojunliu.github.io. All rights reserved.
//
#import <Foundation/Foundation.h>
#define XYUUIDVersion @"1.0.0"
@interface XYUUID : NSObject
/// 随机UUID此值每次都会刷新
+ (NSString *)uuid;
/// 安装UUID每次重新安装此值会刷新
+ (NSString *)uuidForInstall;
/// 开启应用UUID每次开启应用此值会刷新
+ (NSString *)uuidForAppOpen;
/// IDFA开启关闭授权此值会刷新
+ (NSString *)uuidForIDFA;
/// IDFV
+ (NSString *)uuidForIDFV;
/// 设备信息UUID根据设备信息生成能维持一段时间内不变
+ (NSString *)uuidForDeviceInfo;
/// 钥匙串UUID卸载应用保持不变
+ (NSString *)uuidForKeychain;
/// 设备UUID设备唯一标识符
+ (NSString *)uuidForDevice;
@end

View File

@@ -0,0 +1,150 @@
//
// XYUUID.m
// XYUUID
//
// Created by steve on 2016/7/21.
// Copyright © 2020 guojunliu.github.io. All rights reserved.
//
#import "XYUUID.h"
#import <AdSupport/AdSupport.h>
#import <UIKit/UIKit.h>
#import "XYDeviceInfoUUID.h"
#import "XYKeyChain.h"
#if __has_include(<AppTrackingTransparency/AppTrackingTransparency.h>)
#import <AppTrackingTransparency/AppTrackingTransparency.h>
#endif
static NSString *XY_ZeroIdfa = @"00000000-0000-0000-0000-000000000000";
static NSString *STR_XYUUIDForInstall = @"XYUUID-Install";
static NSString *STR_XYUUIDForKeyChain = @"XYUUID-KeyChain-ServiceDomain";
static NSString *STR_XYUUIDForKeyChainAndDeviceOrIdfa = @"XYUUID-KeyChain-Device-Idfa";
//static NSString *STR_XYUUIDForKeyChain = base64Decode:@"Y29tLkhvbGF2ZXJzZS5Ib2xhU3RhdGlzdGljYWw=";
@interface XYUUID ()
@property (nonatomic,copy) NSString *appOpenUUID;
@end
@implementation XYUUID
+ (instancetype)shareManager{
static XYUUID *instantce = nil;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
if (instantce == nil) {
instantce = [[XYUUID alloc] init];
}
});
return instantce;
}
+ (NSString *)uuid {
return [[NSUUID UUID] UUIDString];
}
+ (NSString *)uuidForInstall {
NSString *uuid = [[NSUserDefaults standardUserDefaults] objectForKey:STR_XYUUIDForInstall];
if (uuid && ![uuid isEqualToString:@""]) {
return uuid;
}
uuid = [self uuid];
[[NSUserDefaults standardUserDefaults] setObject:uuid forKey:STR_XYUUIDForInstall];
return uuid;
}
+ (NSString *)uuidForAppOpen {
if ([XYUUID shareManager].appOpenUUID && ![[XYUUID shareManager].appOpenUUID isEqualToString:@""]) {
return [XYUUID shareManager].appOpenUUID;
}
NSString *appOpenUUID = [self uuid];
[XYUUID shareManager].appOpenUUID = appOpenUUID;
return appOpenUUID;
}
+ (NSString *)uuidForIDFA {
if (@available(iOS 14.0, *)) {
ATTrackingManagerAuthorizationStatus states = [ATTrackingManager trackingAuthorizationStatus];
if (states == ATTrackingManagerAuthorizationStatusNotDetermined) {
//
return XY_ZeroIdfa;
}
else if (states == ATTrackingManagerAuthorizationStatusRestricted) {
// 使
return XY_ZeroIdfa;
}
else if (states == ATTrackingManagerAuthorizationStatusDenied) {
//
return XY_ZeroIdfa;
}
else if (states == ATTrackingManagerAuthorizationStatusAuthorized) {
NSString *idfa = [[ASIdentifierManager sharedManager].advertisingIdentifier UUIDString];
return idfa;
}
return XY_ZeroIdfa;
}
if (@available(iOS 10.0, *)) {
BOOL canUseIDFA = [ASIdentifierManager sharedManager].advertisingTrackingEnabled; //YES 广idfa NO00000000-0000-0000-0000-000000000000
if (canUseIDFA) {
NSString *idfa = [[[ASIdentifierManager sharedManager] advertisingIdentifier] UUIDString];
return idfa;
}
return XY_ZeroIdfa;
}
// iOS 10广IDFA
NSString *idfa = [[[ASIdentifierManager sharedManager] advertisingIdentifier] UUIDString];
return idfa;
}
+ (NSString *)uuidForIDFV {
NSString *idfv = [UIDevice currentDevice].identifierForVendor.UUIDString;
return idfv;
}
+ (NSString *)uuidForDeviceInfo {
NSString *uuid = [XYDeviceInfoUUID createDeviceInfoUUID];
return uuid;
}
+ (NSString *)uuidForKeychain {
NSString *uuid = [XYKeyChain getDataWithServiceDomain:STR_XYUUIDForKeyChain];
if (uuid && ![uuid isEqualToString:@""]) {
return uuid;
}
uuid = [self uuid];
[XYKeyChain setData:uuid serviceDomain:STR_XYUUIDForKeyChain];
return uuid;
}
+ (NSString *)uuidForDevice {
NSString *deviceUUID = [XYKeyChain getDataWithServiceDomain:STR_XYUUIDForKeyChainAndDeviceOrIdfa];
if (deviceUUID && ![deviceUUID isEqualToString:@""] && ![deviceUUID isEqualToString:XY_ZeroIdfa]) {
return deviceUUID;
}
NSString *idfa = [self uuidForIDFA];
if (idfa && ![idfa isEqualToString:@""] && ![idfa isEqualToString:XY_ZeroIdfa]) {
[XYKeyChain setData:idfa serviceDomain:STR_XYUUIDForKeyChainAndDeviceOrIdfa];
return idfa;
}
NSString *deviceInfoUUID = [self uuidForDeviceInfo];
if (deviceInfoUUID && ![deviceInfoUUID isEqualToString:@""]) {
[XYKeyChain setData:deviceInfoUUID serviceDomain:STR_XYUUIDForKeyChainAndDeviceOrIdfa];
return deviceInfoUUID;
}
NSString *uuid = [self uuid];
if (uuid && ![uuid isEqualToString:@""]) {
[XYKeyChain setData:uuid serviceDomain:STR_XYUUIDForKeyChainAndDeviceOrIdfa];
return uuid;
}
return @"";
}
@end