iphone DNS解析和网络测试

iphone DNS解析和网络测试

#import  <CFNetwork/CFHost.h>
#import <netinet/in.h>
#import <netdb.h> 
#import <SystemConfiguration/SystemConfiguration.h>

#pragma mark 
-
#pragma mark DNS解析和网络测试
- (NSString * ) getAddressFromArray:(CFArrayRef) addresses
{
    
struct  sockaddr   * addr;
    
char              ipAddress[INET6_ADDRSTRLEN];
    CFIndex          index, count;
    
int               err;
    
    assert(addresses 
!=  NULL);
    
    
    count 
=  CFArrayGetCount(addresses);
    
for  (index  =   0 ; index  <  count; index ++ ) {
        addr 
=  ( struct  sockaddr  * )CFDataGetBytePtr(CFArrayGetValueAtIndex(addresses, index));
        assert(addr 
!=  NULL);
        
        
/*  getnameinfo coverts an IPv4 or IPv6 address into a text string.  */
        err 
=  getnameinfo(addr, addr -> sa_len, ipAddress, INET6_ADDRSTRLEN, NULL,  0 , NI_NUMERICHOST);
        
if  (err  ==   0 ) {
            NSLog(
@" 解析到ip地址:%s\n " , ipAddress);
        } 
else  {
            NSLog(
@" 地址格式转换错误:%d\n " , err);
        }
    }
    
return     [[[NSString alloc] initWithFormat: @" %s " ,ipAddress] autorelease]; // 这里只返回最后一个,一般认为只有一个地址
}


- ( bool )getReachability:(CFDataRef) data withNameOrAddress:(CFStringRef) nameOrAddress
{
    SCNetworkConnectionFlags  
* flags;
    CFIndex                   length;
    
char                        * input;
    Boolean                   success;
    
    assert(data 
!=  NULL);
    assert(nameOrAddress 
!=  NULL);
    
    
/*  CFStringGetMaximumSizeForEncoding determines max bytes a string of specified length will take up if encoded.  */
    length 
=  CFStringGetMaximumSizeForEncoding(CFStringGetLength(nameOrAddress), kCFStringEncodingASCII);
    input 
=  malloc(length  +   1 );
    assert(input 
!=  NULL);
    
    success 
=  CFStringGetCString(nameOrAddress, input, length  +   1 , kCFStringEncodingASCII);
    assert(success);
    
    flags 
=  (SCNetworkConnectionFlags  * )CFDataGetBytePtr(data);
    assert (flags 
!=  NULL);
    
    
/*  If you only have a PPP interface enabled, the flags will be 0 because of a bug. <rdar://problem/3627771>  */
    
if  ( * flags  ==   0 ) NSLog( @" %s -> Reachability Unknown\n " , input);
    
    
if  ( * flags  &  kSCNetworkFlagsTransientConnection)  NSLog( @" %s -> Transient Connection\n " ,  input);
    
if  ( * flags  &  kSCNetworkFlagsReachable)           {
        NSLog(
@" %s -> Reachable\n " ,             input);
        success 
=  YES;
    }
else  {
        success 
=  NO;
    }
    
if  ( * flags  &  kSCNetworkFlagsConnectionRequired)   NSLog( @" %s -> Connection Required\n " ,   input);
    
if  ( * flags  &  kSCNetworkFlagsConnectionAutomatic)  NSLog( @" %s -> Connection Automatic\n " ,  input);
    
if  ( * flags  &  kSCNetworkFlagsInterventionRequired) NSLog( @" %s -> Intervention Required\n " , input);
    
if  ( * flags  &  kSCNetworkFlagsIsLocalAddress)       NSLog( @" %s -> Is Local Address\n " ,      input);
    
if  ( * flags  &  kSCNetworkFlagsIsDirect)             NSLog( @" %s -> Is Direct\n " ,             input);
    
    free(input);
    
return  success;
}

- ( void ) serverResoluton{

    CFStringRef             hostName 
=  (CFStringRef)self.serverInfo.serverAddress; 
    CFHostRef            host;
    CFStreamError        error;
    Boolean              success;
    CFArrayRef             addressArray;
    CFDataRef             ReachableData;
    
    assert(hostName 
!=  NULL);
    
    
/*  Creates a new host object with the given name.  */
    host 
=  CFHostCreateWithName(kCFAllocatorDefault, hostName);
    assert(host 
!=  NULL);
    
    success 
=  CFHostStartInfoResolution(host, kCFHostAddresses,  & error);
    
if  ( ! success) {
        NSLog(
@" CFHostStartInfoResolution 返回错误 (%d, %ld) " , error.domain, error.error); // 如果解析地址失败,使用直接指定IP
        NSLog( @" 启用直接指定IP:%@ " ,self.serverInfo.serverIPAddress);
        [self.serverInfo.serverAddress release];
        self.serverInfo.serverAddress 
=  self.serverInfo.serverIPAddress;
    }
else  {
        addressArray 
=  CFHostGetAddressing(host, nil);
        [self.serverInfo.serverAddress release];
        self.serverInfo.serverAddress 
=  [[NSString alloc] initWithFormat: @" %@ " ,[self getAddressFromArray:addressArray]];
        NSLog(
@" 替换地址为:%@ " , self.serverInfo.serverAddress);
    }
    
    
// 使用新地址来确认可连接性
    hostName  =  (CFStringRef)self.serverInfo.serverAddress;
    host 
=  CFHostCreateWithName(kCFAllocatorDefault, hostName);
    success 
=  CFHostStartInfoResolution(host, kCFHostReachability,  & error);
    
if  ( ! success) {
        NSLog(
@" CFHostStartInfoResolution 返回错误 (%d, %ld) " , error.domain, error.error);
        
// 暂不知到这里会在什么情况下发生
    } else  {
        ReachableData 
=  CFHostGetReachability(host, nil);
        success 
=  [self getReachability:ReachableData withNameOrAddress:(CFStringRef)hostName];
        
if  ( ! success) {
            [self.serverInfo.serverAddress release];
            self.serverInfo.serverAddress 
=  self.serverInfo.serverAddressBak; // 在这里添加备用服务器
        }
    }    

}

你可能感兴趣的:(iphone DNS解析和网络测试)