From ba3a6ea2b0ab60ac66db0add9f98a042c8c62477 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Konstantin=20K=C3=A4fer?= Date: Tue, 26 May 2015 11:08:31 +0200 Subject: update Reachability with latest version --- platform/darwin/reachability.m | 228 +++++++++++++++-------------------------- 1 file changed, 85 insertions(+), 143 deletions(-) (limited to 'platform/darwin') diff --git a/platform/darwin/reachability.m b/platform/darwin/reachability.m index 8234659402..b0818b8838 100644 --- a/platform/darwin/reachability.m +++ b/platform/darwin/reachability.m @@ -25,34 +25,35 @@ POSSIBILITY OF SUCH DAMAGE. */ -#import +#import "Reachability.h" + +#import +#import +#import +#import +#import +#import NSString *const kReachabilityChangedNotification = @"kReachabilityChangedNotification"; + @interface Reachability () @property (nonatomic, assign) SCNetworkReachabilityRef reachabilityRef; - - -#if NEEDS_DISPATCH_RETAIN_RELEASE -@property (nonatomic, assign) dispatch_queue_t reachabilitySerialQueue; -#else @property (nonatomic, strong) dispatch_queue_t reachabilitySerialQueue; -#endif - - -@property (nonatomic, strong) id reachabilityObject; +@property (nonatomic, strong) id reachabilityObject; -(void)reachabilityChanged:(SCNetworkReachabilityFlags)flags; -(BOOL)isReachableWithFlags:(SCNetworkReachabilityFlags)flags; @end + static NSString *reachabilityFlags(SCNetworkReachabilityFlags flags) { return [NSString stringWithFormat:@"%c%c %c%c%c%c%c%c%c", -#if TARGET_OS_IPHONE +#if TARGET_OS_IPHONE (flags & kSCNetworkReachabilityFlagsIsWWAN) ? 'W' : '-', #else 'X', @@ -71,11 +72,8 @@ static NSString *reachabilityFlags(SCNetworkReachabilityFlags flags) static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkReachabilityFlags flags, void* info) { #pragma unused (target) -#if __has_feature(objc_arc) + Reachability *reachability = ((__bridge Reachability*)info); -#else - Reachability *reachability = ((Reachability*)info); -#endif // We probably don't need an autoreleasepool here, as GCD docs state each queue has its own autorelease pool, // but what the heck eh? @@ -88,59 +86,40 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea @implementation Reachability -@synthesize reachabilityRef; -@synthesize reachabilitySerialQueue; - -@synthesize reachableOnWWAN; - -@synthesize reachableBlock; -@synthesize unreachableBlock; - -@synthesize reachabilityObject; - #pragma mark - Class Constructor Methods -+(Reachability*)reachabilityWithHostName:(NSString*)hostname ++(instancetype)reachabilityWithHostName:(NSString*)hostname { return [Reachability reachabilityWithHostname:hostname]; } -+(Reachability*)reachabilityWithHostname:(NSString*)hostname ++(instancetype)reachabilityWithHostname:(NSString*)hostname { SCNetworkReachabilityRef ref = SCNetworkReachabilityCreateWithName(NULL, [hostname UTF8String]); if (ref) { id reachability = [[self alloc] initWithReachabilityRef:ref]; -#if __has_feature(objc_arc) return reachability; -#else - return [reachability autorelease]; -#endif - } return nil; } -+(Reachability *)reachabilityWithAddress:(const struct sockaddr_in *)hostAddress ++(instancetype)reachabilityWithAddress:(void *)hostAddress { SCNetworkReachabilityRef ref = SCNetworkReachabilityCreateWithAddress(kCFAllocatorDefault, (const struct sockaddr*)hostAddress); if (ref) { id reachability = [[self alloc] initWithReachabilityRef:ref]; -#if __has_feature(objc_arc) return reachability; -#else - return [reachability autorelease]; -#endif } return nil; } -+(Reachability *)reachabilityForInternetConnection ++(instancetype)reachabilityForInternetConnection { struct sockaddr_in zeroAddress; bzero(&zeroAddress, sizeof(zeroAddress)); @@ -150,7 +129,7 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea return [self reachabilityWithAddress:&zeroAddress]; } -+(Reachability*)reachabilityForLocalWiFi ++(instancetype)reachabilityForLocalWiFi { struct sockaddr_in localWifiAddress; bzero(&localWifiAddress, sizeof(localWifiAddress)); @@ -165,13 +144,18 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea // Initialization methods --(Reachability *)initWithReachabilityRef:(SCNetworkReachabilityRef)ref +-(instancetype)initWithReachabilityRef:(SCNetworkReachabilityRef)ref { self = [super init]; if (self != nil) { self.reachableOnWWAN = YES; self.reachabilityRef = ref; + + // We need to create a serial queue. + // We allocate this once for the lifetime of the notifier. + + self.reachabilitySerialQueue = dispatch_queue_create("com.tonymillion.reachability", NULL); } return self; @@ -187,14 +171,9 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea self.reachabilityRef = nil; } - self.reachableBlock = nil; - self.unreachableBlock = nil; - -#if !(__has_feature(objc_arc)) - [super dealloc]; -#endif - - + self.reachableBlock = nil; + self.unreachableBlock = nil; + self.reachabilitySerialQueue = nil; } #pragma mark - Notifier Methods @@ -206,75 +185,46 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea -(BOOL)startNotifier { - SCNetworkReachabilityContext context = { 0, NULL, NULL, NULL, NULL }; - - // this should do a retain on ourself, so as long as we're in notifier mode we shouldn't disappear out from under ourselves - // woah - self.reachabilityObject = self; - - - - // First, we need to create a serial queue. - // We allocate this once for the lifetime of the notifier. - self.reachabilitySerialQueue = dispatch_queue_create("com.tonymillion.reachability", NULL); - if(self.reachabilitySerialQueue == nil) + // allow start notifier to be called multiple times + if(self.reachabilityObject && (self.reachabilityObject == self)) { - return NO; + return YES; } -#if __has_feature(objc_arc) + + SCNetworkReachabilityContext context = { 0, NULL, NULL, NULL, NULL }; context.info = (__bridge void *)self; -#else - context.info = (void *)self; -#endif - if (!SCNetworkReachabilitySetCallback(self.reachabilityRef, TMReachabilityCallback, &context)) + if(SCNetworkReachabilitySetCallback(self.reachabilityRef, TMReachabilityCallback, &context)) { + // Set it as our reachability queue, which will retain the queue + if(SCNetworkReachabilitySetDispatchQueue(self.reachabilityRef, self.reachabilitySerialQueue)) + { + // this should do a retain on ourself, so as long as we're in notifier mode we shouldn't disappear out from under ourselves + // woah + self.reachabilityObject = self; + return YES; + } + else + { #ifdef DEBUG - NSLog(@"SCNetworkReachabilitySetCallback() failed: %s", SCErrorString(SCError())); + NSLog(@"SCNetworkReachabilitySetDispatchQueue() failed: %s", SCErrorString(SCError())); #endif - // Clear out the dispatch queue - if(self.reachabilitySerialQueue) - { -#if NEEDS_DISPATCH_RETAIN_RELEASE - dispatch_release(self.reachabilitySerialQueue); -#endif - self.reachabilitySerialQueue = nil; + // UH OH - FAILURE - stop any callbacks! + SCNetworkReachabilitySetCallback(self.reachabilityRef, NULL, NULL); } - - self.reachabilityObject = nil; - - return NO; } - - // Set it as our reachability queue, which will retain the queue - if(!SCNetworkReachabilitySetDispatchQueue(self.reachabilityRef, self.reachabilitySerialQueue)) + else { #ifdef DEBUG - NSLog(@"SCNetworkReachabilitySetDispatchQueue() failed: %s", SCErrorString(SCError())); -#endif - - // UH OH - FAILURE! - - // First stop, any callbacks! - SCNetworkReachabilitySetCallback(self.reachabilityRef, NULL, NULL); - - // Then clear out the dispatch queue. - if(self.reachabilitySerialQueue) - { -#if NEEDS_DISPATCH_RETAIN_RELEASE - dispatch_release(self.reachabilitySerialQueue); + NSLog(@"SCNetworkReachabilitySetCallback() failed: %s", SCErrorString(SCError())); #endif - self.reachabilitySerialQueue = nil; - } - - self.reachabilityObject = nil; - - return NO; } - return YES; + // if we get here we fail at the internet + self.reachabilityObject = nil; + return NO; } -(void)stopNotifier @@ -285,14 +235,6 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea // Unregister target from the GCD serial dispatch queue. SCNetworkReachabilitySetDispatchQueue(self.reachabilityRef, NULL); - if(self.reachabilitySerialQueue) - { -#if NEEDS_DISPATCH_RETAIN_RELEASE - dispatch_release(self.reachabilitySerialQueue); -#endif - self.reachabilitySerialQueue = nil; - } - self.reachabilityObject = nil; } @@ -318,7 +260,7 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea if( (flags & testcase) == testcase ) connectionUP = NO; -#if TARGET_OS_IPHONE +#if TARGET_OS_IPHONE if(flags & kSCNetworkReachabilityFlagsIsWWAN) { // We're on 3G. @@ -345,11 +287,11 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea -(BOOL)isReachableViaWWAN { -#if TARGET_OS_IPHONE +#if TARGET_OS_IPHONE SCNetworkReachabilityFlags flags = 0; - if(SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + if(SCNetworkReachabilityGetFlags(self.reachabilityRef, &flags)) { // Check we're REACHABLE if(flags & kSCNetworkReachabilityFlagsReachable) @@ -370,12 +312,12 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea { SCNetworkReachabilityFlags flags = 0; - if(SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + if(SCNetworkReachabilityGetFlags(self.reachabilityRef, &flags)) { // Check we're reachable if((flags & kSCNetworkReachabilityFlagsReachable)) { -#if TARGET_OS_IPHONE +#if TARGET_OS_IPHONE // Check we're NOT on WWAN if((flags & kSCNetworkReachabilityFlagsIsWWAN)) { @@ -401,10 +343,10 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea { SCNetworkReachabilityFlags flags; - if(SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + if(SCNetworkReachabilityGetFlags(self.reachabilityRef, &flags)) { - return (flags & kSCNetworkReachabilityFlagsConnectionRequired); - } + return (flags & kSCNetworkReachabilityFlagsConnectionRequired); + } return NO; } @@ -412,15 +354,15 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea // Dynamic, on demand connection? -(BOOL)isConnectionOnDemand { - SCNetworkReachabilityFlags flags; + SCNetworkReachabilityFlags flags; - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + if (SCNetworkReachabilityGetFlags(self.reachabilityRef, &flags)) { - return ((flags & kSCNetworkReachabilityFlagsConnectionRequired) && - (flags & (kSCNetworkReachabilityFlagsConnectionOnTraffic | kSCNetworkReachabilityFlagsConnectionOnDemand))); - } + return ((flags & kSCNetworkReachabilityFlagsConnectionRequired) && + (flags & (kSCNetworkReachabilityFlagsConnectionOnTraffic | kSCNetworkReachabilityFlagsConnectionOnDemand))); + } - return NO; + return NO; } // Is user intervention required? @@ -428,13 +370,13 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea { SCNetworkReachabilityFlags flags; - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + if (SCNetworkReachabilityGetFlags(self.reachabilityRef, &flags)) { - return ((flags & kSCNetworkReachabilityFlagsConnectionRequired) && - (flags & kSCNetworkReachabilityFlagsInterventionRequired)); - } + return ((flags & kSCNetworkReachabilityFlagsConnectionRequired) && + (flags & kSCNetworkReachabilityFlagsInterventionRequired)); + } - return NO; + return NO; } @@ -447,7 +389,7 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea if([self isReachableViaWiFi]) return ReachableViaWiFi; -#if TARGET_OS_IPHONE +#if TARGET_OS_IPHONE return ReachableViaWWAN; #endif } @@ -459,7 +401,7 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea { SCNetworkReachabilityFlags flags = 0; - if(SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + if(SCNetworkReachabilityGetFlags(self.reachabilityRef, &flags)) { return flags; } @@ -469,19 +411,19 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea -(NSString*)currentReachabilityString { - NetworkStatus temp = [self currentReachabilityStatus]; + NetworkStatus temp = [self currentReachabilityStatus]; - if(temp == reachableOnWWAN) - { + if(temp == ReachableViaWWAN) + { // Updated for the fact that we have CDMA phones now! - return NSLocalizedString(@"Cellular", @""); - } - if (temp == ReachableViaWiFi) - { - return NSLocalizedString(@"WiFi", @""); - } - - return NSLocalizedString(@"No Connection", @""); + return NSLocalizedString(@"Cellular", @""); + } + if (temp == ReachableViaWiFi) + { + return NSLocalizedString(@"WiFi", @""); + } + + return NSLocalizedString(@"No Connection", @""); } -(NSString*)currentReachabilityFlags @@ -519,8 +461,8 @@ static void TMReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkRea - (NSString *) description { - NSString *description = [NSString stringWithFormat:@"<%@: %#x>", - NSStringFromClass([self class]), (unsigned int) self]; + NSString *description = [NSString stringWithFormat:@"<%@: %#x (%@)>", + NSStringFromClass([self class]), (unsigned int) self, [self currentReachabilityFlags]]; return description; } -- cgit v1.2.1