iPhone开发关于UDID和UUID的一些理解

一.UDID(Unique Device Identifier) 
UDID是Unique Device Identifier的缩写,中文意思是设备唯一标识. 
在很多需要限制一台设备一个账号的应用中经常会用到,在Symbian时代,我们是使用IMEI作为设备的唯一标识的,可惜的是Apple官方不允许开发者获得设备的IMEI. 
 
 
ios5 sdk中的获取方法: 
[UIDevice currentDevice] uniqueIdentifier] 
 
 
uniqueIdentifier在UIDevice.h中的定义如下: 
@property(nonatomic,readonly,retain) NSString    *uniqueIdentifier  __OSX_AVAILABLE_BUT_DEPRECATED(__MAC_NA,__MAC_NA,__IPHONE_2_0,__IPHONE_5_0);  // a string unique to each device based on various hardware info. 
意思是iOS2.0以上及iOS5.0以下的系统可用,但不建议使用.Apple有可能在ios5.0之后删除该函数. 
经过测试,未越狱的iPhone,系统版本为5.0.1,依然可以获取UDID. 
 
 
但是我们需要注意的一点是,对于已越狱了的设备,UDID并不是唯一的.使用Cydia插件UDIDFaker,可以为每一个应用分配不同的UDID. 
所以UDID作为标识唯一设备的用途已经不大了. 
 
 
二.UUID(Universally Unique Identifier) 
UUID是Universally Unique Identifier的缩写,中文意思是通用唯一识别码. 
由网上资料显示,UUID是一个软件建构的标准,也是被开源软件基金会(Open Software Foundation,OSF)的组织在分布式计算环境(Distributed Computing Environment,DCE)领域的一部份.UUID的目的,是让分布式系统中的所有元素,都能有唯一的辨识资讯,而不需要透过中央控制端来做辨识资讯的指定. 
 
 
根据以上定义可知,同一设备上的不同应用的UUID是互斥的,即能在改设备上标识应用.但是并没有明确指出能标识出装有同一应用的不同设备,但是根据我推测,这个UUID应该是根据设备标识和应用标识生成唯一标识,再经过加密而来的(纯推测). 
 
 
iOS中获取UUID的代码如下: 
-(NSString*) uuid {  
    CFUUIDRef puuid = CFUUIDCreate( nil );  
    CFStringRef uuidString = CFUUIDCreateString( nil, puuid );  
    NSString * result = (NSString *)CFStringCreateCopy( NULL, uuidString);  
    CFRelease(puuid);  
    CFRelease(uuidString);  
    return [result autorelease];  

 
 
虽然UUID是官方提出的一种替代UDID的建议方案,但网上有资料说UUID不能保证在以后的系统升级后(IOS6,7)还能用. 
 
 
经过我测试目前,UUID在IOS4和IOS5下均可以使用,而且UUID每次生成的值都不一样,需要开发者自行保存UUID. 
如果使用UUID为标识保存用户的资料在网络上,当用户重装软件后,UUID的值就可能会发生改变(基本上可说是百分百会发生改变),用户则无法重新下载原来的网络资料. 
 
 
三.一个可行的解决方案 
经过上述的探讨,我们不难发现,无论是使用UDID或是UUID,我们的目的通常都是为了让用户可以自动注册,而不需要账号密码.而使用UDID和UUID作为用户的ID也并不是毫无缺陷. 
现在网上有一现成的解决方案,使用设备的Mac地址,因为Mac地址也是唯一的.unix有系统调用可以获取Mac地址.但有些事情需要注意: 
1.iPhone可能有多个Mac地址,wifi的地址,以及SIM卡的地址.一般来讲,我们取en0的地址,因为他是iPhone的wifi的地址,是肯定存在的.(例外情况依然有:市面上依然存在一部分联通的阉割版无wifi的iPhone) 
2.Mac地址涉及到隐私,不应该胡乱将用户的Mac地址传播!所以我们需要将Mac地址进行hash之后,才能作为DeviceId上传. 
 
 
关于第一个注意点的问题,经过我测试,没有Wifi功能的iPhone3GS一样可以获得Mac地址,所以这应该是目前标识设备唯一最好的一个解决方案. 
 
 
解决方案github下载地址github。com/gekitz/UIDevice-with-UniqueIdentifier-for-iOS-5 
 
 

原文地址www。waaile。com转自我的博客,欢迎大家留言指点! 



我还没在发布的应用上试过获取MAC地址,但是你获取MAC再经过HASH后进行传递,苹果应该是不会拒绝的. 
这里,我顺带给出mac地址的获取代码吧 
#include <sys/socket.h> // Per msqr 
#include <sys/sysctl.h> 
#include <net/if.h> 
#include <net/if_dl.h> 
 
// Return the local MAC addy 
// Courtesy of FreeBSD hackers email list 
// Accidentally munged during previous update. Fixed thanks to erica sadun & mlamb. 
- (NSString *)macaddress{ 
     
    int                 mib[6]; 
    size_t              len; 
    char                *buf; 
    unsigned char       *ptr; 
    struct if_msghdr    *ifm; 
    struct sockaddr_dl  *sdl; 
     
    mib[0] = CTL_NET; 
    mib[1] = AF_ROUTE; 
    mib[2] = 0; 
    mib[3] = AF_LINK; 
    mib[4] = NET_RT_IFLIST; 
     
    if ((mib[5] = if_nametoindex("en0")) == 0) { 
        printf("Error: if_nametoindex error\n"); 
        return NULL; 
    } 
     
    if (sysctl(mib, 6, NULL, &len, NULL, 0) < 0) { 
        printf("Error: sysctl, take 1\n"); 
        return NULL; 
    } 
     
    if ((buf = malloc(len)) == NULL) { 
        printf("Could not allocate memory. error!\n"); 
        return NULL; 
    } 
     
    if (sysctl(mib, 6, buf, &len, NULL, 0) < 0) { 
        printf("Error: sysctl, take 2"); 
        free(buf); 
        return NULL; 
    } 
     
    ifm = (struct if_msghdr *)buf; 
    sdl = (struct sockaddr_dl *)(ifm + 1); 
    ptr = (unsigned char *)LLADDR(sdl); 
    NSString *outstring = [NSString stringWithFormat:@"%02X:%02X:%02X:%02X:%02X:%02X",  
                           *ptr, *(ptr+1), *(ptr+2), *(ptr+3), *(ptr+4), *(ptr+5)]; 
    free(buf); 
     
    return outstring; 

你可能感兴趣的:(iPhone开发关于UDID和UUID的一些理解)