diff --git a/.gitignore b/.gitignore index f36b7ae7..8bafd02a 100644 --- a/.gitignore +++ b/.gitignore @@ -10,4 +10,5 @@ profile *.pbxuser *.mode1v3 External/GHUnit/* -.svn \ No newline at end of file +.svn +*.orig \ No newline at end of file diff --git a/ASIHTTPRequest-OSX/ASIHTTPRequestOSX-Prefix.pch b/ASIHTTPRequest-OSX/ASIHTTPRequestOSX-Prefix.pch new file mode 100644 index 00000000..025d8b78 --- /dev/null +++ b/ASIHTTPRequest-OSX/ASIHTTPRequestOSX-Prefix.pch @@ -0,0 +1,7 @@ +// +// Prefix header for all source files of the 'ASIHTTPRequest' target in the 'ASIHTTPRequest' project +// + +#ifdef __OBJC__ + #import +#endif diff --git a/ASIHTTPRequest-iOS/ASIHTTPRequestIOS-Prefix.pch b/ASIHTTPRequest-iOS/ASIHTTPRequestIOS-Prefix.pch new file mode 100644 index 00000000..b95ddb94 --- /dev/null +++ b/ASIHTTPRequest-iOS/ASIHTTPRequestIOS-Prefix.pch @@ -0,0 +1,7 @@ +// +// Prefix header for all source files of the 'ASIHTTPRequestMobile' target in the 'ASIHTTPRequestMobile' project +// + +#ifdef __OBJC__ + #import +#endif diff --git a/ASIHTTPResourceBundle/ASIHTTPResourceBundle-Info.plist b/ASIHTTPResourceBundle/ASIHTTPResourceBundle-Info.plist new file mode 100644 index 00000000..cd664d5e --- /dev/null +++ b/ASIHTTPResourceBundle/ASIHTTPResourceBundle-Info.plist @@ -0,0 +1,44 @@ + + + + + CFBundleDevelopmentRegion + English + CFBundleExecutable + ${EXECUTABLE_NAME} + CFBundleIconFile + + CFBundleIdentifier + com.intelligentmobiles.${PRODUCT_NAME:rfc1034identifier} + CFBundleInfoDictionaryVersion + 6.0 + CFBundleName + ${PRODUCT_NAME} + CFBundlePackageType + BNDL + CFBundleShortVersionString + 1.0 + CFBundleSignature + ???? + CFBundleVersion + 1 + CFPlugInDynamicRegisterFunction + + CFPlugInDynamicRegistration + NO + CFPlugInFactories + + 00000000-0000-0000-0000-000000000000 + MyFactoryFunction + + CFPlugInTypes + + 00000000-0000-0000-0000-000000000000 + + 00000000-0000-0000-0000-000000000000 + + + CFPlugInUnloadFunction + + + diff --git a/ASIHTTPResourceBundle/ASIHTTPResourceBundle-Prefix.pch b/ASIHTTPResourceBundle/ASIHTTPResourceBundle-Prefix.pch new file mode 100644 index 00000000..35d76409 --- /dev/null +++ b/ASIHTTPResourceBundle/ASIHTTPResourceBundle-Prefix.pch @@ -0,0 +1,9 @@ +// +// Prefix header +// +// The contents of this file are implicitly included at the beginning of every source file. +// + +#ifdef __OBJC__ + #import +#endif diff --git a/ASIHTTPResourceBundle/en.lproj/InfoPlist.strings b/ASIHTTPResourceBundle/en.lproj/InfoPlist.strings new file mode 100644 index 00000000..477b28ff --- /dev/null +++ b/ASIHTTPResourceBundle/en.lproj/InfoPlist.strings @@ -0,0 +1,2 @@ +/* Localized versions of Info.plist keys */ + diff --git a/Classes/ASIAuthenticationDialog.m b/Classes/ASIAuthenticationDialog.m index 255a6849..f1f2fcc3 100644 --- a/Classes/ASIAuthenticationDialog.m +++ b/Classes/ASIAuthenticationDialog.m @@ -51,7 +51,7 @@ @implementation ASIAuthenticationDialog + (void)initialize { if (self == [ASIAuthenticationDialog class]) { - requestsNeedingAuthentication = [[NSMutableArray array] retain]; + requestsNeedingAuthentication = [NSMutableArray array]; } } @@ -98,12 +98,7 @@ - (void)dealloc [[NSNotificationCenter defaultCenter] removeObserver:self name:UIDeviceOrientationDidChangeNotification object:nil]; } [[NSNotificationCenter defaultCenter] removeObserver:self name:UIKeyboardWillShowNotification object:nil]; - - [request release]; - [tableView release]; [presentingController.view removeFromSuperview]; - [presentingController release]; - [super dealloc]; } #pragma mark keyboard notifications @@ -217,18 +212,15 @@ - (UITextField *)domainField + (void)dismiss { if ([sharedDialog respondsToSelector:@selector(presentingViewController)]) - [[sharedDialog presentingViewController] dismissModalViewControllerAnimated:YES]; + [[sharedDialog presentingViewController] dismissViewControllerAnimated:YES completion:nil]; else - [[sharedDialog parentViewController] dismissModalViewControllerAnimated:YES]; + [[sharedDialog parentViewController] dismissViewControllerAnimated:YES completion:nil]; } - (void)viewDidDisappear:(BOOL)animated { - [self retain]; - [sharedDialog release]; - sharedDialog = nil; [self performSelector:@selector(presentNextDialog) withObject:nil afterDelay:0]; - [self release]; + sharedDialog = nil; } - (void)dismiss @@ -237,9 +229,9 @@ - (void)dismiss [[self class] dismiss]; } else { if ([self respondsToSelector:@selector(presentingViewController)]) - [[self presentingViewController] dismissModalViewControllerAnimated:YES]; + [[self presentingViewController] dismissViewControllerAnimated:YES completion:nil]; else - [[self parentViewController] dismissModalViewControllerAnimated:YES]; + [[self parentViewController] dismissViewControllerAnimated:YES completion:nil]; } } @@ -273,10 +265,10 @@ - (void)show } // Setup toolbar - UINavigationBar *bar = [[[UINavigationBar alloc] init] autorelease]; + UINavigationBar *bar = [[UINavigationBar alloc] init]; [bar setAutoresizingMask:UIViewAutoresizingFlexibleWidth]; - UINavigationItem *navItem = [[[UINavigationItem alloc] init] autorelease]; + UINavigationItem *navItem = [[UINavigationItem alloc] init]; bar.items = [NSArray arrayWithObject:navItem]; [[self view] addSubview:bar]; @@ -290,8 +282,8 @@ - (void)show [navItem setTitle:[[[self request] url] host]]; } - [navItem setLeftBarButtonItem:[[[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemCancel target:self action:@selector(cancelAuthenticationFromDialog:)] autorelease]]; - [navItem setRightBarButtonItem:[[[UIBarButtonItem alloc] initWithTitle:@"Login" style:UIBarButtonItemStyleDone target:self action:@selector(loginWithCredentialsFromDialog:)] autorelease]]; + [navItem setLeftBarButtonItem:[[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemCancel target:self action:@selector(cancelAuthenticationFromDialog:)]]; + [navItem setRightBarButtonItem:[[UIBarButtonItem alloc] initWithTitle:@"Login" style:UIBarButtonItemStyleDone target:self action:@selector(loginWithCredentialsFromDialog:)]]; // We show the login form in a table view, similar to Safari's authentication dialog [bar sizeToFit]; @@ -299,7 +291,7 @@ - (void)show f.origin.y = [bar frame].size.height; f.size.height -= f.origin.y; - [self setTableView:[[[UITableView alloc] initWithFrame:f style:UITableViewStyleGrouped] autorelease]]; + [self setTableView:[[UITableView alloc] initWithFrame:f style:UITableViewStyleGrouped]]; [[self tableView] setDelegate:self]; [[self tableView] setDataSource:self]; [[self tableView] setAutoresizingMask:UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight]; @@ -315,7 +307,7 @@ - (void)show } #endif - [[self presentingController] presentModalViewController:self animated:YES]; + [[self presentingController] presentViewController:self animated:YES completion:nil]; } #pragma mark button callbacks @@ -431,7 +423,7 @@ - (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInte - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { #if __IPHONE_OS_VERSION_MIN_REQUIRED >= __IPHONE_3_0 - UITableViewCell *cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:nil] autorelease]; + UITableViewCell *cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:nil]; #else UITableViewCell *cell = [[[UITableViewCell alloc] initWithFrame:CGRectMake(0,0,0,0) reuseIdentifier:nil] autorelease]; #endif @@ -439,7 +431,7 @@ - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(N [cell setSelectionStyle:UITableViewCellSelectionStyleNone]; CGRect f = CGRectInset([cell bounds], 10, 10); - UITextField *textField = [[[UITextField alloc] initWithFrame:f] autorelease]; + UITextField *textField = [[UITextField alloc] initWithFrame:f]; [textField setAutoresizingMask:UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight]; [textField setAutocapitalizationType:UITextAutocapitalizationTypeNone]; [textField setAutocorrectionType:UITextAutocorrectionTypeNo]; diff --git a/Classes/ASICacheDelegate.h b/Classes/ASICacheDelegate.h index 060cda59..9de64a84 100644 --- a/Classes/ASICacheDelegate.h +++ b/Classes/ASICacheDelegate.h @@ -15,37 +15,37 @@ // Note that some of the behaviours below are mutally exclusive - you cannot combine ASIAskServerIfModifiedWhenStaleCachePolicy and ASIAskServerIfModifiedCachePolicy, for example. typedef enum _ASICachePolicy { - // The default cache policy. When you set a request to use this, it will use the cache's defaultCachePolicy - // ASIDownloadCache's default cache policy is 'ASIAskServerIfModifiedWhenStaleCachePolicy' - ASIUseDefaultCachePolicy = 0, + // The default cache policy. When you set a request to use this, it will use the cache's defaultCachePolicy + // ASIDownloadCache's default cache policy is 'ASIAskServerIfModifiedWhenStaleCachePolicy' + ASIUseDefaultCachePolicy = 0, - // Tell the request not to read from the cache - ASIDoNotReadFromCacheCachePolicy = 1, + // Tell the request not to read from the cache + ASIDoNotReadFromCacheCachePolicy = 1, - // The the request not to write to the cache - ASIDoNotWriteToCacheCachePolicy = 2, + // The the request not to write to the cache + ASIDoNotWriteToCacheCachePolicy = 2, - // Ask the server if there is an updated version of this resource (using a conditional GET) ONLY when the cached data is stale - ASIAskServerIfModifiedWhenStaleCachePolicy = 4, + // Ask the server if there is an updated version of this resource (using a conditional GET) ONLY when the cached data is stale + ASIAskServerIfModifiedWhenStaleCachePolicy = 4, - // Always ask the server if there is an updated version of this resource (using a conditional GET) - ASIAskServerIfModifiedCachePolicy = 8, + // Always ask the server if there is an updated version of this resource (using a conditional GET) + ASIAskServerIfModifiedCachePolicy = 8, - // If cached data exists, use it even if it is stale. This means requests will not talk to the server unless the resource they are requesting is not in the cache - ASIOnlyLoadIfNotCachedCachePolicy = 16, + // If cached data exists, use it even if it is stale. This means requests will not talk to the server unless the resource they are requesting is not in the cache + ASIOnlyLoadIfNotCachedCachePolicy = 16, - // If cached data exists, use it even if it is stale. If cached data does not exist, stop (will not set an error on the request) - ASIDontLoadCachePolicy = 32, + // If cached data exists, use it even if it is stale. If cached data does not exist, stop (will not set an error on the request) + ASIDontLoadCachePolicy = 32, - // Specifies that cached data may be used if the request fails. If cached data is used, the request will succeed without error. Usually used in combination with other options above. - ASIFallbackToCacheIfLoadFailsCachePolicy = 64 + // Specifies that cached data may be used if the request fails. If cached data is used, the request will succeed without error. Usually used in combination with other options above. + ASIFallbackToCacheIfLoadFailsCachePolicy = 64 } ASICachePolicy; // Cache storage policies control whether cached data persists between application launches (ASICachePermanentlyCacheStoragePolicy) or not (ASICacheForSessionDurationCacheStoragePolicy) // Calling [ASIHTTPRequest clearSession] will remove any data stored using ASICacheForSessionDurationCacheStoragePolicy typedef enum _ASICacheStoragePolicy { - ASICacheForSessionDurationCacheStoragePolicy = 0, - ASICachePermanentlyCacheStoragePolicy = 1 + ASICacheForSessionDurationCacheStoragePolicy = 0, + ASICachePermanentlyCacheStoragePolicy = 1 } ASICacheStoragePolicy; diff --git a/Classes/ASIDataCompressor.h b/Classes/ASIDataCompressor.h index ae0e441a..206ce7ff 100644 --- a/Classes/ASIDataCompressor.h +++ b/Classes/ASIDataCompressor.h @@ -14,12 +14,11 @@ #import @interface ASIDataCompressor : NSObject { - BOOL streamReady; - z_stream zStream; + z_stream zStream; } // Convenience constructor will call setupStream for you -+ (id)compressor; ++ (instancetype)compressor; // Compress the passed chunk of data // Passing YES for shouldFinish will finalize the deflated data - you must pass YES when you are on the last chunk of data diff --git a/Classes/ASIDataCompressor.m b/Classes/ASIDataCompressor.m index c9a5cd55..2c5e847f 100644 --- a/Classes/ASIDataCompressor.m +++ b/Classes/ASIDataCompressor.m @@ -18,24 +18,23 @@ + (NSError *)deflateErrorWithCode:(int)code; @implementation ASIDataCompressor -+ (id)compressor ++ (instancetype)compressor { - ASIDataCompressor *compressor = [[[self alloc] init] autorelease]; + ASIDataCompressor *compressor = [[self alloc] init]; [compressor setupStream]; return compressor; } - (void)dealloc { - if (streamReady) { + if (_streamReady) { [self closeStream]; } - [super dealloc]; } - (NSError *)setupStream { - if (streamReady) { + if (_streamReady) { return nil; } // Setup the inflate stream @@ -48,17 +47,17 @@ - (NSError *)setupStream if (status != Z_OK) { return [[self class] deflateErrorWithCode:status]; } - streamReady = YES; + _streamReady = YES; return nil; } - (NSError *)closeStream { - if (!streamReady) { + if (!_streamReady) { return nil; } // Close the deflate stream - streamReady = NO; + _streamReady = NO; int status = deflateEnd(&zStream); if (status != Z_OK) { return [[self class] deflateErrorWithCode:status]; @@ -125,7 +124,7 @@ + (NSData *)compressData:(NSData*)uncompressedData error:(NSError **)err + (BOOL)compressDataFromFile:(NSString *)sourcePath toFile:(NSString *)destinationPath error:(NSError **)err { - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; // Create an empty file at the destination path if (![fileManager createFileAtPath:destinationPath contents:[NSData data] attributes:nil]) { @@ -215,5 +214,4 @@ + (NSError *)deflateErrorWithCode:(int)code return [NSError errorWithDomain:NetworkRequestErrorDomain code:ASICompressionError userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"Compression of data failed with code %d",code],NSLocalizedDescriptionKey,nil]]; } -@synthesize streamReady; @end diff --git a/Classes/ASIDataDecompressor.h b/Classes/ASIDataDecompressor.h index 8be8f9b5..8b32b33e 100644 --- a/Classes/ASIDataDecompressor.h +++ b/Classes/ASIDataDecompressor.h @@ -14,12 +14,11 @@ #import @interface ASIDataDecompressor : NSObject { - BOOL streamReady; z_stream zStream; } // Convenience constructor will call setupStream for you -+ (id)decompressor; ++ (instancetype)decompressor; // Uncompress the passed chunk of data - (NSData *)uncompressBytes:(Bytef *)bytes length:(NSUInteger)length error:(NSError **)err; diff --git a/Classes/ASIDataDecompressor.m b/Classes/ASIDataDecompressor.m index e84a1e31..200c1f9f 100644 --- a/Classes/ASIDataDecompressor.m +++ b/Classes/ASIDataDecompressor.m @@ -17,24 +17,23 @@ + (NSError *)inflateErrorWithCode:(int)code; @implementation ASIDataDecompressor -+ (id)decompressor ++ (instancetype)decompressor { - ASIDataDecompressor *decompressor = [[[self alloc] init] autorelease]; + ASIDataDecompressor *decompressor = [[self alloc] init]; [decompressor setupStream]; return decompressor; } - (void)dealloc { - if (streamReady) { + if (_streamReady) { [self closeStream]; } - [super dealloc]; } - (NSError *)setupStream { - if (streamReady) { + if (_streamReady) { return nil; } // Setup the inflate stream @@ -47,17 +46,17 @@ - (NSError *)setupStream if (status != Z_OK) { return [[self class] inflateErrorWithCode:status]; } - streamReady = YES; + _streamReady = YES; return nil; } - (NSError *)closeStream { - if (!streamReady) { + if (!_streamReady) { return nil; } // Close the inflate stream - streamReady = NO; + _streamReady = NO; int status = inflateEnd(&zStream); if (status != Z_OK) { return [[self class] inflateErrorWithCode:status]; @@ -121,7 +120,7 @@ + (NSData *)uncompressData:(NSData*)compressedData error:(NSError **)err + (BOOL)uncompressDataFromFile:(NSString *)sourcePath toFile:(NSString *)destinationPath error:(NSError **)err { - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; // Create an empty file at the destination path if (![fileManager createFileAtPath:destinationPath contents:[NSData data] attributes:nil]) { @@ -214,5 +213,4 @@ + (NSError *)inflateErrorWithCode:(int)code return [NSError errorWithDomain:NetworkRequestErrorDomain code:ASICompressionError userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"Decompression of data failed with code %d",code],NSLocalizedDescriptionKey,nil]]; } -@synthesize streamReady; @end diff --git a/Classes/ASIDownloadCache.h b/Classes/ASIDownloadCache.h index a2df9084..af9eefcf 100644 --- a/Classes/ASIDownloadCache.h +++ b/Classes/ASIDownloadCache.h @@ -16,10 +16,6 @@ // Defaults to ASIAskServerIfModifiedWhenStaleCachePolicy ASICachePolicy defaultCachePolicy; - // The directory in which cached data will be stored - // Defaults to a directory called 'ASIHTTPRequestCache' in the temporary directory - NSString *storagePath; - // Mediates access to the cache NSRecursiveLock *accessLock; @@ -40,6 +36,9 @@ + (NSArray *)fileExtensionsToHandleAsHTML; @property (assign, nonatomic) ASICachePolicy defaultCachePolicy; + +// The directory in which cached data will be stored +// Defaults to a directory called 'ASIHTTPRequestCache' in the temporary directory @property (retain, nonatomic) NSString *storagePath; @property (retain) NSRecursiveLock *accessLock; @property (assign) BOOL shouldRespectCacheControlHeaders; diff --git a/Classes/ASIDownloadCache.m b/Classes/ASIDownloadCache.m index 93da36fb..d5b499ba 100644 --- a/Classes/ASIDownloadCache.m +++ b/Classes/ASIDownloadCache.m @@ -37,7 +37,7 @@ - (id)init self = [super init]; [self setShouldRespectCacheControlHeaders:YES]; [self setDefaultCachePolicy:ASIUseDefaultCachePolicy]; - [self setAccessLock:[[[NSRecursiveLock alloc] init] autorelease]]; + [self setAccessLock:[[NSRecursiveLock alloc] init]]; return self; } @@ -54,30 +54,13 @@ + (id)sharedCache return sharedCache; } -- (void)dealloc -{ - [storagePath release]; - [accessLock release]; - [super dealloc]; -} - -- (NSString *)storagePath -{ - [[self accessLock] lock]; - NSString *p = [[storagePath retain] autorelease]; - [[self accessLock] unlock]; - return p; -} - - - (void)setStoragePath:(NSString *)path { [[self accessLock] lock]; [self clearCachedResponsesForStoragePolicy:ASICacheForSessionDurationCacheStoragePolicy]; - [storagePath release]; - storagePath = [path retain]; + _storagePath = path; - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; BOOL isDirectory = NO; NSArray *directories = [NSArray arrayWithObjects:path,[path stringByAppendingPathComponent:sessionCacheFolder],[path stringByAppendingPathComponent:permanentCacheFolder],nil]; @@ -176,7 +159,6 @@ - (void)storeResponseForRequest:(ASIHTTPRequest *)request maxAge:(NSTimeInterval [manager removeItemAtPath:dataPath error:&error]; } [manager copyItemAtPath:[request downloadDestinationPath] toPath:dataPath error:&error]; - [manager release]; } [[self accessLock] unlock]; } @@ -231,7 +213,7 @@ - (NSString *)pathToFile:(NSString *)file return nil; } - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; // Look in the session store NSString *dataPath = [[[self storagePath] stringByAppendingPathComponent:sessionCacheFolder] stringByAppendingPathComponent:file]; @@ -293,7 +275,7 @@ - (void)removeCachedDataForURL:(NSURL *)url [[self accessLock] unlock]; return; } - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; NSString *path = [self pathToCachedResponseHeadersForURL:url]; if (path) { @@ -400,7 +382,7 @@ - (void)clearCachedResponsesForStoragePolicy:(ASICacheStoragePolicy)storagePolic } NSString *path = [[self storagePath] stringByAppendingPathComponent:(storagePolicy == ASICacheForSessionDurationCacheStoragePolicy ? sessionCacheFolder : permanentCacheFolder)]; - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; BOOL isDirectory = NO; BOOL exists = [fileManager fileExistsAtPath:path isDirectory:&isDirectory]; @@ -507,7 +489,6 @@ - (BOOL)canUseCachedDataForRequest:(ASIHTTPRequest *)request return NO; } -@synthesize storagePath; @synthesize defaultCachePolicy; @synthesize accessLock; @synthesize shouldRespectCacheControlHeaders; diff --git a/Classes/ASIFormDataRequest.h b/Classes/ASIFormDataRequest.h index 670995f1..439b0551 100644 --- a/Classes/ASIFormDataRequest.h +++ b/Classes/ASIFormDataRequest.h @@ -16,24 +16,7 @@ typedef enum _ASIPostFormat { } ASIPostFormat; -@interface ASIFormDataRequest : ASIHTTPRequest { - - // Parameters that will be POSTed to the url - NSMutableArray *postData; - - // Files that will be POSTed to the url - NSMutableArray *fileData; - - ASIPostFormat postFormat; - - NSStringEncoding stringEncoding; - -#if DEBUG_FORM_DATA_REQUEST - // Will store a string version of the request body that will be printed to the console when ASIHTTPREQUEST_DEBUG is set in GCC_PREPROCESSOR_DEFINITIONS - NSString *debugBodyString; -#endif - -} +@interface ASIFormDataRequest : ASIHTTPRequest #pragma mark utilities - (NSString*)encodeURL:(NSString *)string; @@ -73,4 +56,5 @@ typedef enum _ASIPostFormat { @property (assign) ASIPostFormat postFormat; @property (assign) NSStringEncoding stringEncoding; + @end diff --git a/Classes/ASIFormDataRequest.m b/Classes/ASIFormDataRequest.m index 2d812a04..438abf63 100644 --- a/Classes/ASIFormDataRequest.m +++ b/Classes/ASIFormDataRequest.m @@ -15,11 +15,16 @@ - (void)buildMultipartFormDataPostBody; - (void)buildURLEncodedPostBody; - (void)appendPostString:(NSString *)string; +// Parameters that will be POSTed to the url @property (retain) NSMutableArray *postData; + +// Files that will be POSTed to the url @property (retain) NSMutableArray *fileData; #if DEBUG_FORM_DATA_REQUEST - (void)addToDebugBody:(NSString *)string; + +// Will store a string version of the request body that will be printed to the console when ASIHTTPREQUEST_DEBUG is set in GCC_PREPROCESSOR_DEFINITIONS @property (retain, nonatomic) NSString *debugBodyString; #endif @@ -30,7 +35,7 @@ @implementation ASIFormDataRequest #pragma mark utilities - (NSString*)encodeURL:(NSString *)string { - NSString *newString = [NSMakeCollectable(CFURLCreateStringByAddingPercentEscapes(kCFAllocatorDefault, (CFStringRef)string, NULL, CFSTR(":/?#[]@!$ &'()*+,;=\"<>%{}|\\^~`"), CFStringConvertNSStringEncodingToEncoding([self stringEncoding]))) autorelease]; + NSString *newString = CFBridgingRelease(CFURLCreateStringByAddingPercentEscapes(kCFAllocatorDefault, (__bridge CFStringRef)string, NULL, CFSTR(":/?#[]@!$ &'()*+,;=\"<>%{}|\\^~`"), CFStringConvertNSStringEncodingToEncoding([self stringEncoding]))); if (newString) { return newString; } @@ -41,7 +46,7 @@ - (NSString*)encodeURL:(NSString *)string + (id)requestWithURL:(NSURL *)newURL { - return [[[self alloc] initWithURL:newURL] autorelease]; + return [[self alloc] initWithURL:newURL]; } - (id)initWithURL:(NSURL *)newURL @@ -53,17 +58,6 @@ - (id)initWithURL:(NSURL *)newURL return self; } -- (void)dealloc -{ -#if DEBUG_FORM_DATA_REQUEST - [debugBodyString release]; -#endif - - [postData release]; - [fileData release]; - [super dealloc]; -} - #pragma mark setup request - (void)addPostValue:(id )value forKey:(NSString *)key @@ -103,7 +97,7 @@ - (void)addFile:(NSString *)filePath forKey:(NSString *)key - (void)addFile:(NSString *)filePath withFileName:(NSString *)fileName andContentType:(NSString *)contentType forKey:(NSString *)key { BOOL isDirectory = NO; - BOOL fileExists = [[[[NSFileManager alloc] init] autorelease] fileExistsAtPath:filePath isDirectory:&isDirectory]; + BOOL fileExists = [[[NSFileManager alloc] init] fileExistsAtPath:filePath isDirectory:&isDirectory]; if (!fileExists || isDirectory) { [self failWithError:[NSError errorWithDomain:NetworkRequestErrorDomain code:ASIInternalErrorWhileBuildingRequestType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"No file exists at %@",filePath],NSLocalizedDescriptionKey,nil]]]; } @@ -220,11 +214,11 @@ - (void)buildMultipartFormDataPostBody [self addToDebugBody:@"\r\n==== Building a multipart/form-data body ====\r\n"]; #endif - NSString *charset = (NSString *)CFStringConvertEncodingToIANACharSetName(CFStringConvertNSStringEncodingToEncoding([self stringEncoding])); + NSString *charset = (__bridge NSString *)CFStringConvertEncodingToIANACharSetName(CFStringConvertNSStringEncodingToEncoding([self stringEncoding])); // We don't bother to check if post data contains the boundary, since it's pretty unlikely that it does. CFUUIDRef uuid = CFUUIDCreate(nil); - NSString *uuidString = [(NSString*)CFUUIDCreateString(nil, uuid) autorelease]; + NSString *uuidString = (NSString*)CFBridgingRelease(CFUUIDCreateString(nil, uuid)); CFRelease(uuid); NSString *stringBoundary = [NSString stringWithFormat:@"0xKhTmLbOuNdArY-%@",uuidString]; @@ -344,19 +338,12 @@ - (void)addToDebugBody:(NSString *)string - (id)copyWithZone:(NSZone *)zone { ASIFormDataRequest *newRequest = [super copyWithZone:zone]; - [newRequest setPostData:[[[self postData] mutableCopyWithZone:zone] autorelease]]; - [newRequest setFileData:[[[self fileData] mutableCopyWithZone:zone] autorelease]]; + [newRequest setPostData:[[self postData] mutableCopyWithZone:zone]]; + [newRequest setFileData:[[self fileData] mutableCopyWithZone:zone]]; [newRequest setPostFormat:[self postFormat]]; [newRequest setStringEncoding:[self stringEncoding]]; [newRequest setRequestMethod:[self requestMethod]]; return newRequest; } -@synthesize postData; -@synthesize fileData; -@synthesize postFormat; -@synthesize stringEncoding; -#if DEBUG_FORM_DATA_REQUEST -@synthesize debugBodyString; -#endif @end diff --git a/Classes/ASIHTTPRequest.h b/Classes/ASIHTTPRequest.h index ed6edc87..3e7b2112 100644 --- a/Classes/ASIHTTPRequest.h +++ b/Classes/ASIHTTPRequest.h @@ -12,10 +12,10 @@ #import #if TARGET_OS_IPHONE - #import - #if __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_4_0 - #import // Necessary for background task support - #endif + #import + #if __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_4_0 + #import // Necessary for background task support + #endif #endif #import @@ -31,22 +31,22 @@ extern NSString *ASIHTTPRequestVersion; // Make targeting different platforms more reliable // See: http://www.blumtnwerx.com/blog/2009/06/cross-sdk-code-hygiene-in-xcode/ #ifndef __IPHONE_3_2 - #define __IPHONE_3_2 30200 + #define __IPHONE_3_2 30200 #endif #ifndef __IPHONE_4_0 - #define __IPHONE_4_0 40000 + #define __IPHONE_4_0 40000 #endif #ifndef __MAC_10_5 - #define __MAC_10_5 1050 + #define __MAC_10_5 1050 #endif #ifndef __MAC_10_6 - #define __MAC_10_6 1060 + #define __MAC_10_6 1060 #endif typedef enum _ASIAuthenticationState { - ASINoAuthenticationNeededYet = 0, - ASIHTTPAuthenticationNeeded = 1, - ASIProxyAuthenticationNeeded = 2 + ASINoAuthenticationNeededYet = 0, + ASIHTTPAuthenticationNeeded = 1, + ASIProxyAuthenticationNeeded = 2 } ASIAuthenticationState; typedef enum _ASINetworkErrorType { @@ -57,11 +57,11 @@ typedef enum _ASINetworkErrorType { ASIUnableToCreateRequestErrorType = 5, ASIInternalErrorWhileBuildingRequestType = 6, ASIInternalErrorWhileApplyingCredentialsType = 7, - ASIFileManagementError = 8, - ASITooMuchRedirectionErrorType = 9, - ASIUnhandledExceptionError = 10, - ASICompressionError = 11 - + ASIFileManagementError = 8, + ASITooMuchRedirectionErrorType = 9, + ASIUnhandledExceptionError = 10, + ASICompressionError = 11 + } ASINetworkErrorType; @@ -82,474 +82,188 @@ typedef void (^ASIDataBlock)(NSData *data); #endif @interface ASIHTTPRequest : NSOperation { - - // The url for this operation, should include GET params in the query string where appropriate - NSURL *url; - - // Will always contain the original url used for making the request (the value of url can change when a request is redirected) - NSURL *originalURL; - - // Temporarily stores the url we are about to redirect to. Will be nil again when we do redirect - NSURL *redirectURL; - - // The delegate - will be notified of various changes in state via the ASIHTTPRequestDelegate protocol - id delegate; - - // Another delegate that is also notified of request status changes and progress updates - // Generally, you won't use this directly, but ASINetworkQueue sets itself as the queue so it can proxy updates to its own delegates - // NOTE: WILL BE RETAINED BY THE REQUEST - id queue; - - // HTTP method to use (eg: GET / POST / PUT / DELETE / HEAD etc). Defaults to GET - NSString *requestMethod; - - // Request body - only used when the whole body is stored in memory (shouldStreamPostDataFromDisk is false) - NSMutableData *postBody; - - // gzipped request body used when shouldCompressRequestBody is YES - NSData *compressedPostBody; - - // When true, post body will be streamed from a file on disk, rather than loaded into memory at once (useful for large uploads) - // Automatically set to true in ASIFormDataRequests when using setFile:forKey: - BOOL shouldStreamPostDataFromDisk; - - // Path to file used to store post body (when shouldStreamPostDataFromDisk is true) - // You can set this yourself - useful if you want to PUT a file from local disk - NSString *postBodyFilePath; - - // Path to a temporary file used to store a deflated post body (when shouldCompressPostBody is YES) - NSString *compressedPostBodyFilePath; - - // Set to true when ASIHTTPRequest automatically created a temporary file containing the request body (when true, the file at postBodyFilePath will be deleted at the end of the request) - BOOL didCreateTemporaryPostDataFile; - - // Used when writing to the post body when shouldStreamPostDataFromDisk is true (via appendPostData: or appendPostDataFromFile:) - NSOutputStream *postBodyWriteStream; - - // Used for reading from the post body when sending the request - NSInputStream *postBodyReadStream; - - // Dictionary for custom HTTP request headers - NSMutableDictionary *requestHeaders; - - // Set to YES when the request header dictionary has been populated, used to prevent this happening more than once - BOOL haveBuiltRequestHeaders; - - // Will be populated with HTTP response headers from the server - NSDictionary *responseHeaders; - - // Can be used to manually insert cookie headers to a request, but it's more likely that sessionCookies will do this for you - NSMutableArray *requestCookies; - - // Will be populated with cookies - NSArray *responseCookies; - - // If use useCookiePersistence is true, network requests will present valid cookies from previous requests - BOOL useCookiePersistence; - - // If useKeychainPersistence is true, network requests will attempt to read credentials from the keychain, and will save them in the keychain when they are successfully presented - BOOL useKeychainPersistence; - - // If useSessionPersistence is true, network requests will save credentials and reuse for the duration of the session (until clearSession is called) - BOOL useSessionPersistence; - - // If allowCompressedResponse is true, requests will inform the server they can accept compressed data, and will automatically decompress gzipped responses. Default is true. - BOOL allowCompressedResponse; - - // If shouldCompressRequestBody is true, the request body will be gzipped. Default is false. - // You will probably need to enable this feature on your webserver to make this work. Tested with apache only. - BOOL shouldCompressRequestBody; - - // When downloadDestinationPath is set, the result of this request will be downloaded to the file at this location - // If downloadDestinationPath is not set, download data will be stored in memory - NSString *downloadDestinationPath; - - // The location that files will be downloaded to. Once a download is complete, files will be decompressed (if necessary) and moved to downloadDestinationPath - NSString *temporaryFileDownloadPath; - - // If the response is gzipped and shouldWaitToInflateCompressedResponses is NO, a file will be created at this path containing the inflated response as it comes in - NSString *temporaryUncompressedDataDownloadPath; - - // Used for writing data to a file when downloadDestinationPath is set - NSOutputStream *fileDownloadOutputStream; - - NSOutputStream *inflatedFileDownloadOutputStream; - - // When the request fails or completes successfully, complete will be true - BOOL complete; - + // Set to YES when the request header dictionary has been populated, used to prevent this happening more than once + BOOL haveBuiltRequestHeaders; + + // If useKeychainPersistence is true, network requests will attempt to read credentials from the keychain, and will save them in the keychain when they are successfully presented + BOOL useKeychainPersistence; + + BOOL _complete; // external "finished" indicator, subject of KVO notifications; updates after 'complete' BOOL finished; // True if our 'cancel' selector has been called BOOL cancelled; - // If an error occurs, error will contain an NSError - // If error code is = ASIConnectionFailureErrorType (1, Connection failure occurred) - inspect [[error userInfo] objectForKey:NSUnderlyingErrorKey] for more information - NSError *error; - - // Username and password used for authentication - NSString *username; - NSString *password; - - // User-Agent for this request - NSString *userAgentString; - - // Domain used for NTLM authentication - NSString *domain; - - // Username and password used for proxy authentication - NSString *proxyUsername; - NSString *proxyPassword; - - // Domain used for NTLM proxy authentication - NSString *proxyDomain; - - // Delegate for displaying upload progress (usually an NSProgressIndicator, but you can supply a different object and handle this yourself) - id uploadProgressDelegate; - - // Delegate for displaying download progress (usually an NSProgressIndicator, but you can supply a different object and handle this yourself) - id downloadProgressDelegate; - - // Whether we've seen the headers of the response yet + // Whether we've seen the headers of the response yet BOOL haveExaminedHeaders; - - // Data we receive will be stored here. Data may be compressed unless allowCompressedResponse is false - you should use [request responseData] instead in most cases - NSMutableData *rawResponseData; - - // Used for sending and receiving data - CFHTTPMessageRef request; - NSInputStream *readStream; - - // Used for authentication - CFHTTPAuthenticationRef requestAuthentication; - NSDictionary *requestCredentials; - - // Used during NTLM authentication - int authenticationRetryCount; - - // Authentication scheme (Basic, Digest, NTLM) - // If you are using Basic authentication and want to force ASIHTTPRequest to send an authorization header without waiting for a 401, you must set this to (NSString *)kCFHTTPAuthenticationSchemeBasic - NSString *authenticationScheme; - - // Realm for authentication when credentials are required - NSString *authenticationRealm; - - // When YES, ASIHTTPRequest will present a dialog allowing users to enter credentials when no-matching credentials were found for a server that requires authentication - // The dialog will not be shown if your delegate responds to authenticationNeededForRequest: - // Default is NO. - BOOL shouldPresentAuthenticationDialog; - - // When YES, ASIHTTPRequest will present a dialog allowing users to enter credentials when no-matching credentials were found for a proxy server that requires authentication - // The dialog will not be shown if your delegate responds to proxyAuthenticationNeededForRequest: - // Default is YES (basically, because most people won't want the hassle of adding support for authenticating proxies to their apps) - BOOL shouldPresentProxyAuthenticationDialog; - - // Used for proxy authentication - CFHTTPAuthenticationRef proxyAuthentication; - NSDictionary *proxyCredentials; - - // Used during authentication with an NTLM proxy - int proxyAuthenticationRetryCount; - - // Authentication scheme for the proxy (Basic, Digest, NTLM) - NSString *proxyAuthenticationScheme; - - // Realm for proxy authentication when credentials are required - NSString *proxyAuthenticationRealm; - - // HTTP status code, eg: 200 = OK, 404 = Not found etc - int responseStatusCode; - - // Description of the HTTP status code - NSString *responseStatusMessage; - - // Size of the response - unsigned long long contentLength; - - // Size of the partially downloaded content - unsigned long long partialDownloadSize; - - // Size of the POST payload - unsigned long long postLength; - - // The total amount of downloaded data - unsigned long long totalBytesRead; - - // The total amount of uploaded data - unsigned long long totalBytesSent; - - // Last amount of data read (used for incrementing progress) - unsigned long long lastBytesRead; - - // Last amount of data sent (used for incrementing progress) - unsigned long long lastBytesSent; - - // This lock prevents the operation from being cancelled at an inopportune moment - NSRecursiveLock *cancelledLock; - - // Called on the delegate (if implemented) when the request starts. Default is requestStarted: - SEL didStartSelector; - - // Called on the delegate (if implemented) when the request receives response headers. Default is request:didReceiveResponseHeaders: - SEL didReceiveResponseHeadersSelector; - - // Called on the delegate (if implemented) when the request receives a Location header and shouldRedirect is YES - // The delegate can then change the url if needed, and can restart the request by calling [request redirectToURL:], or simply cancel it - SEL willRedirectSelector; - - // Called on the delegate (if implemented) when the request completes successfully. Default is requestFinished: - SEL didFinishSelector; - - // Called on the delegate (if implemented) when the request fails. Default is requestFailed: - SEL didFailSelector; - - // Called on the delegate (if implemented) when the request receives data. Default is request:didReceiveData: - // If you set this and implement the method in your delegate, you must handle the data yourself - ASIHTTPRequest will not populate responseData or write the data to downloadDestinationPath - SEL didReceiveDataSelector; - - // Used for recording when something last happened during the request, we will compare this value with the current date to time out requests when appropriate - NSDate *lastActivityTime; - - // Number of seconds to wait before timing out - default is 10 - NSTimeInterval timeOutSeconds; - - // Will be YES when a HEAD request will handle the content-length before this request starts - BOOL shouldResetUploadProgress; - BOOL shouldResetDownloadProgress; - - // Used by HEAD requests when showAccurateProgress is YES to preset the content-length for this request - ASIHTTPRequest *mainRequest; - - // When NO, this request will only update the progress indicator when it completes - // When YES, this request will update the progress indicator according to how much data it has received so far - // The default for requests is YES - // Also see the comments in ASINetworkQueue.h - BOOL showAccurateProgress; - - // Used to ensure the progress indicator is only incremented once when showAccurateProgress = NO - BOOL updatedProgress; - - // Prevents the body of the post being built more than once (largely for subclasses) - BOOL haveBuiltPostBody; - - // Used internally, may reflect the size of the internal buffer used by CFNetwork - // POST / PUT operations with body sizes greater than uploadBufferSize will not timeout unless more than uploadBufferSize bytes have been sent - // Likely to be 32KB on iPhone 3.0, 128KB on Mac OS X Leopard and iPhone 2.2.x - unsigned long long uploadBufferSize; - - // Text encoding for responses that do not send a Content-Type with a charset value. Defaults to NSISOLatin1StringEncoding - NSStringEncoding defaultResponseEncoding; - - // The text encoding of the response, will be defaultResponseEncoding if the server didn't specify. Can't be set. - NSStringEncoding responseEncoding; - - // Tells ASIHTTPRequest not to delete partial downloads, and allows it to use an existing file to resume a download. Defaults to NO. - BOOL allowResumeForFileDownloads; - - // Custom user information associated with the request (not sent to the server) - NSDictionary *userInfo; - NSInteger tag; - - // Use HTTP 1.0 rather than 1.1 (defaults to false) - BOOL useHTTPVersionOne; - - // When YES, requests will automatically redirect when they get a HTTP 30x header (defaults to YES) - BOOL shouldRedirect; - - // Used internally to tell the main loop we need to stop and retry with a new url - BOOL needsRedirect; - - // Incremented every time this request redirects. When it reaches 5, we give up - int redirectCount; - - // When NO, requests will not check the secure certificate is valid (use for self-signed certificates during development, DO NOT USE IN PRODUCTION) Default is YES - BOOL validatesSecureCertificate; + // Used for sending and receiving data + CFHTTPMessageRef request; + + // Used for authentication + CFHTTPAuthenticationRef requestAuthentication; + + // Used during NTLM authentication + int authenticationRetryCount; + + // When YES, ASIHTTPRequest will present a dialog allowing users to enter credentials when no-matching credentials were found for a server that requires authentication + // The dialog will not be shown if your delegate responds to authenticationNeededForRequest: + // Default is NO. + BOOL shouldPresentAuthenticationDialog; + + // Used for proxy authentication + CFHTTPAuthenticationRef proxyAuthentication; + + // Used during authentication with an NTLM proxy + int proxyAuthenticationRetryCount; + + // HTTP status code, eg: 200 = OK, 404 = Not found etc + int responseStatusCode; + + // Size of the partially downloaded content + unsigned long long partialDownloadSize; + + // Size of the POST payload + unsigned long long postLength; + + // Last amount of data read (used for incrementing progress) + unsigned long long lastBytesRead; + + // Last amount of data sent (used for incrementing progress) + unsigned long long lastBytesSent; + // Used to ensure the progress indicator is only incremented once when showAccurateProgress = NO + BOOL updatedProgress; + + // Used internally, may reflect the size of the internal buffer used by CFNetwork + // POST / PUT operations with body sizes greater than uploadBufferSize will not timeout unless more than uploadBufferSize bytes have been sent + // Likely to be 32KB on iPhone 3.0, 128KB on Mac OS X Leopard and iPhone 2.2.x + unsigned long long uploadBufferSize; + + // The text encoding of the response, will be defaultResponseEncoding if the server didn't specify. Can't be set. + NSStringEncoding responseEncoding; + + // Tells ASIHTTPRequest not to delete partial downloads, and allows it to use an existing file to resume a download. Defaults to NO. + BOOL allowResumeForFileDownloads; + + NSInteger tag; + + // Use HTTP 1.0 rather than 1.1 (defaults to false) + BOOL useHTTPVersionOne; + + // Incremented every time this request redirects. When it reaches 5, we give up + int redirectCount; + // If not nil and the URL scheme is https, CFNetwork configured to supply a client certificate SecIdentityRef clientCertificateIdentity; - NSArray *clientCertificates; - - // Details on the proxy to use - you could set these yourself, but it's probably best to let ASIHTTPRequest detect the system proxy settings - NSString *proxyHost; - int proxyPort; - - // ASIHTTPRequest will assume kCFProxyTypeHTTP if the proxy type could not be automatically determined - // Set to kCFProxyTypeSOCKS if you are manually configuring a SOCKS proxy - NSString *proxyType; - - // URL for a PAC (Proxy Auto Configuration) file. If you want to set this yourself, it's probably best if you use a local file - NSURL *PACurl; - - // See ASIAuthenticationState values above. 0 == default == No authentication needed yet - ASIAuthenticationState authenticationNeeded; - - // When YES, ASIHTTPRequests will present credentials from the session store for requests to the same server before being asked for them - // This avoids an extra round trip for requests after authentication has succeeded, which is much for efficient for authenticated requests with large bodies, or on slower connections - // Set to NO to only present credentials when explicitly asked for them - // This only affects credentials stored in the session cache when useSessionPersistence is YES. Credentials from the keychain are never presented unless the server asks for them - // Default is YES - // For requests using Basic authentication, set authenticationScheme to (NSString *)kCFHTTPAuthenticationSchemeBasic, and credentials can be sent on the very first request when shouldPresentCredentialsBeforeChallenge is YES - BOOL shouldPresentCredentialsBeforeChallenge; - - // YES when the request hasn't finished yet. Will still be YES even if the request isn't doing anything (eg it's waiting for delegate authentication). READ-ONLY - BOOL inProgress; - - // Used internally to track whether the stream is scheduled on the run loop or not - // Bandwidth throttling can unschedule the stream to slow things down while a request is in progress - BOOL readStreamIsScheduled; - - // Set to allow a request to automatically retry itself on timeout - // Default is zero - timeout will stop the request - int numberOfTimesToRetryOnTimeout; - - // The number of times this request has retried (when numberOfTimesToRetryOnTimeout > 0) - int retryCount; - - // Temporarily set to YES when a closed connection forces a retry (internally, this stops ASIHTTPRequest cleaning up a temporary post body) - BOOL willRetryRequest; - - // When YES, requests will keep the connection to the server alive for a while to allow subsequent requests to re-use it for a substantial speed-boost - // Persistent connections will not be used if the server explicitly closes the connection - // Default is YES - BOOL shouldAttemptPersistentConnection; - - // Number of seconds to keep an inactive persistent connection open on the client side - // Default is 60 - // If we get a keep-alive header, this is this value is replaced with how long the server told us to keep the connection around - // A future date is created from this and used for expiring the connection, this is stored in connectionInfo's expires value - NSTimeInterval persistentConnectionTimeoutSeconds; - - // Set to yes when an appropriate keep-alive header is found - BOOL connectionCanBeReused; - - // Stores information about the persistent connection that is currently in use. - // It may contain: - // * The id we set for a particular connection, incremented every time we want to specify that we need a new connection - // * The date that connection should expire - // * A host, port and scheme for the connection. These are used to determine whether that connection can be reused by a subsequent request (all must match the new request) - // * An id for the request that is currently using the connection. This is used for determining if a connection is available or not (we store a number rather than a reference to the request so we don't need to hang onto a request until the connection expires) - // * A reference to the stream that is currently using the connection. This is necessary because we need to keep the old stream open until we've opened a new one. - // The stream will be closed + released either when another request comes to use the connection, or when the timer fires to tell the connection to expire - NSMutableDictionary *connectionInfo; - - // When set to YES, 301 and 302 automatic redirects will use the original method and and body, according to the HTTP 1.1 standard - // Default is NO (to follow the behaviour of most browsers) - BOOL shouldUseRFC2616RedirectBehaviour; - - // Used internally to record when a request has finished downloading data - BOOL downloadComplete; - - // An ID that uniquely identifies this request - primarily used for debugging persistent connections - NSNumber *requestID; - - // Will be ASIHTTPRequestRunLoopMode for synchronous requests, NSDefaultRunLoopMode for all other requests - NSString *runLoopMode; - - // This timer checks up on the request every 0.25 seconds, and updates progress - NSTimer *statusTimer; - - // The download cache that will be used for this request (use [ASIHTTPRequest setDefaultCache:cache] to configure a default cache - id downloadCache; - - // The cache policy that will be used for this request - See ASICacheDelegate.h for possible values - ASICachePolicy cachePolicy; - - // The cache storage policy that will be used for this request - See ASICacheDelegate.h for possible values - ASICacheStoragePolicy cacheStoragePolicy; - - // Will be true when the response was pulled from the cache rather than downloaded - BOOL didUseCachedResponse; - - // Set secondsToCache to use a custom time interval for expiring the response when it is stored in a cache - NSTimeInterval secondsToCache; - - #if TARGET_OS_IPHONE && __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_4_0 - BOOL shouldContinueWhenAppEntersBackground; - UIBackgroundTaskIdentifier backgroundTask; - #endif - - // When downloading a gzipped response, the request will use this helper object to inflate the response - ASIDataDecompressor *dataDecompressor; - - // Controls how responses with a gzipped encoding are inflated (decompressed) - // When set to YES (This is the default): - // * gzipped responses for requests without a downloadDestinationPath will be inflated only when [request responseData] / [request responseString] is called - // * gzipped responses for requests with a downloadDestinationPath set will be inflated only when the request completes - // - // When set to NO - // All requests will inflate the response as it comes in - // * If the request has no downloadDestinationPath set, the raw (compressed) response is discarded and rawResponseData will contain the decompressed response - // * If the request has a downloadDestinationPath, the raw response will be stored in temporaryFileDownloadPath as normal, the inflated response will be stored in temporaryUncompressedDataDownloadPath - // Once the request completes successfully, the contents of temporaryUncompressedDataDownloadPath are moved into downloadDestinationPath - // - // Setting this to NO may be especially useful for users using ASIHTTPRequest in conjunction with a streaming parser, as it will allow partial gzipped responses to be inflated and passed on to the parser while the request is still running - BOOL shouldWaitToInflateCompressedResponses; - - // Will be YES if this is a request created behind the scenes to download a PAC file - these requests do not attempt to configure their own proxies - BOOL isPACFileRequest; - - // Used for downloading PAC files from http / https webservers - ASIHTTPRequest *PACFileRequest; - - // Used for asynchronously reading PAC files from file:// URLs - NSInputStream *PACFileReadStream; - - // Used for storing PAC data from file URLs as it is downloaded - NSMutableData *PACFileData; - - // Set to YES in startSynchronous. Currently used by proxy detection to download PAC files synchronously when appropriate - BOOL isSynchronous; - - #if NS_BLOCKS_AVAILABLE - //block to execute when request starts - ASIBasicBlock startedBlock; - - //block to execute when headers are received - ASIHeadersBlock headersReceivedBlock; - - //block to execute when request completes successfully - ASIBasicBlock completionBlock; - - //block to execute when request fails - ASIBasicBlock failureBlock; - - //block for when bytes are received - ASIProgressBlock bytesReceivedBlock; - - //block for when bytes are sent - ASIProgressBlock bytesSentBlock; - - //block for when download size is incremented - ASISizeBlock downloadSizeIncrementedBlock; - - //block for when upload size is incremented - ASISizeBlock uploadSizeIncrementedBlock; - - //block for handling raw bytes received - ASIDataBlock dataReceivedBlock; - - //block for handling authentication - ASIBasicBlock authenticationNeededBlock; - - //block for handling proxy authentication - ASIBasicBlock proxyAuthenticationNeededBlock; - + + int proxyPort; + + // See ASIAuthenticationState values above. 0 == default == No authentication needed yet + ASIAuthenticationState authenticationNeeded; + + // YES when the request hasn't finished yet. Will still be YES even if the request isn't doing anything (eg it's waiting for delegate authentication). READ-ONLY + BOOL inProgress; + + // Set to allow a request to automatically retry itself on timeout + // Default is zero - timeout will stop the request + int numberOfTimesToRetryOnTimeout; + + // The number of times this request has retried (when numberOfTimesToRetryOnTimeout > 0) + int retryCount; + + // Temporarily set to YES when a closed connection forces a retry (internally, this stops ASIHTTPRequest cleaning up a temporary post body) + BOOL willRetryRequest; + + + // Set to yes when an appropriate keep-alive header is found + BOOL connectionCanBeReused; + + // When set to YES, 301 and 302 automatic redirects will use the original method and and body, according to the HTTP 1.1 standard + // Default is NO (to follow the behaviour of most browsers) + BOOL shouldUseRFC2616RedirectBehaviour; + + // Used internally to record when a request has finished downloading data + BOOL downloadComplete; + + // The cache policy that will be used for this request - See ASICacheDelegate.h for possible values + ASICachePolicy cachePolicy; + + // The cache storage policy that will be used for this request - See ASICacheDelegate.h for possible values + ASICacheStoragePolicy cacheStoragePolicy; + + // Will be true when the response was pulled from the cache rather than downloaded + BOOL didUseCachedResponse; + + // Set secondsToCache to use a custom time interval for expiring the response when it is stored in a cache + NSTimeInterval secondsToCache; + + #if TARGET_OS_IPHONE && __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_4_0 + BOOL shouldContinueWhenAppEntersBackground; + UIBackgroundTaskIdentifier backgroundTask; + #endif + + // Used for downloading PAC files from http / https webservers + ASIHTTPRequest *PACFileRequest; + + // Used for asynchronously reading PAC files from file:// URLs + NSInputStream *PACFileReadStream; + + // Used for storing PAC data from file URLs as it is downloaded + NSMutableData *PACFileData; + + // Set to YES in startSynchronous. Currently used by proxy detection to download PAC files synchronously when appropriate + BOOL isSynchronous; + + #if NS_BLOCKS_AVAILABLE + //block to execute when request starts + ASIBasicBlock startedBlock; + + //block to execute when headers are received + ASIHeadersBlock headersReceivedBlock; + + //block to execute when request completes successfully + ASIBasicBlock completionBlock; + + //block to execute when request fails + ASIBasicBlock failureBlock; + + //block for when bytes are received + ASIProgressBlock bytesReceivedBlock; + + //block for when bytes are sent + ASIProgressBlock bytesSentBlock; + + //block for when download size is incremented + ASISizeBlock downloadSizeIncrementedBlock; + + //block for when upload size is incremented + ASISizeBlock uploadSizeIncrementedBlock; + + //block for handling raw bytes received + ASIDataBlock dataReceivedBlock; + + //block for handling authentication + ASIBasicBlock authenticationNeededBlock; + + //block for handling proxy authentication + ASIBasicBlock proxyAuthenticationNeededBlock; + //block for handling redirections, if you want to ASIBasicBlock requestRedirectedBlock; - #endif + #endif } #pragma mark init / dealloc // Should be an HTTP or HTTPS url, may include username and password if appropriate -- (id)initWithURL:(NSURL *)newURL; +- (instancetype)initWithURL:(NSURL *)newURL; // Convenience constructor -+ (id)requestWithURL:(NSURL *)newURL; ++ (instancetype)requestWithURL:(NSURL *)newURL; -+ (id)requestWithURL:(NSURL *)newURL usingCache:(id )cache; -+ (id)requestWithURL:(NSURL *)newURL usingCache:(id )cache andCachePolicy:(ASICachePolicy)policy; ++ (instancetype)requestWithURL:(NSURL *)newURL usingCache:(id )cache; ++ (instancetype)requestWithURL:(NSURL *)newURL usingCache:(id )cache andCachePolicy:(ASICachePolicy)policy; #if NS_BLOCKS_AVAILABLE - (void)setStartedBlock:(ASIBasicBlock)aStartedBlock; @@ -638,10 +352,10 @@ typedef void (^ASIDataBlock)(NSData *data); - (void)incrementUploadSizeBy:(long long)length; // Helper method for interacting with progress indicators to abstract the details of different APIS (NSProgressIndicator and UIProgressView) -+ (void)updateProgressIndicator:(id *)indicator withProgress:(unsigned long long)progress ofTotal:(unsigned long long)total; ++ (void)updateProgressIndicator:(id)indicator withProgress:(unsigned long long)progress ofTotal:(unsigned long long)total; // Helper method used for performing invocations on the main thread (used for progress) -+ (void)performSelector:(SEL)selector onTarget:(id *)target withObject:(id)object amount:(void *)amount callerToRetain:(id)caller; ++ (void)performSelector:(SEL)selector onTarget:(id)target withObject:(id)object amount:(void *)amount callerToRetain:(id)caller; #pragma mark talking to delegates @@ -901,104 +615,283 @@ typedef void (^ASIDataBlock)(NSData *data); #pragma mark === -@property (retain) NSString *username; -@property (retain) NSString *password; +// Username and password used for authentication +@property (strong) NSString *username; +@property (strong) NSString *password; + +// User-Agent for this request @property (retain) NSString *userAgentString; + +// Domain used for NTLM authentication @property (retain) NSString *domain; + +// Username and password used for proxy authentication @property (retain) NSString *proxyUsername; + +// Username and password used for proxy authentication @property (retain) NSString *proxyPassword; + +// Domain used for NTLM proxy authentication @property (retain) NSString *proxyDomain; + +// Details on the proxy to use - you could set these yourself, but it's probably best to let ASIHTTPRequest detect the system proxy settings @property (retain) NSString *proxyHost; @property (assign) int proxyPort; + +// ASIHTTPRequest will assume kCFProxyTypeHTTP if the proxy type could not be automatically determined +// Set to kCFProxyTypeSOCKS if you are manually configuring a SOCKS proxy @property (retain) NSString *proxyType; + +// The url for this operation, should include GET params in the query string where appropriate @property (retain,setter=setURL:, nonatomic) NSURL *url; + +// Will always contain the original url used for making the request (the value of url can change when a request is redirected) @property (retain) NSURL *originalURL; -@property (assign, nonatomic) id delegate; + +// The delegate - will be notified of various changes in state via the ASIHTTPRequestDelegate protocol +// id +@property (weak, nonatomic) id delegate; + +// Another delegate that is also notified of request status changes and progress updates +// Generally, you won't use this directly, but ASINetworkQueue sets itself as the queue so it can proxy updates to its own delegates +// id @property (retain, nonatomic) id queue; -@property (assign, nonatomic) id uploadProgressDelegate; -@property (assign, nonatomic) id downloadProgressDelegate; + +// NOTE: WILL BE RETAINED BY THE REQUEST + +// Delegate for displaying upload progress (usually an NSProgressIndicator, but you can supply a different object and handle this yourself) +// id +@property (weak, nonatomic) id uploadProgressDelegate; + +// Delegate for displaying download progress (usually an NSProgressIndicator, but you can supply a different object and handle this yourself) +// id +@property (weak, nonatomic) id downloadProgressDelegate; @property (assign) BOOL useKeychainPersistence; + +// If useSessionPersistence is true, network requests will save credentials and reuse for the duration of the session (until clearSession is called) @property (assign) BOOL useSessionPersistence; + +// When downloadDestinationPath is set, the result of this request will be downloaded to the file at this location +// If downloadDestinationPath is not set, download data will be stored in memory @property (retain) NSString *downloadDestinationPath; + +// The location that files will be downloaded to. Once a download is complete, files will be decompressed (if necessary) and moved to downloadDestinationPath @property (retain) NSString *temporaryFileDownloadPath; + +// If the response is gzipped and shouldWaitToInflateCompressedResponses is NO, a file will be created at this path containing the inflated response as it comes in @property (retain) NSString *temporaryUncompressedDataDownloadPath; + +// Called on the delegate (if implemented) when the request starts. Default is requestStarted: @property (assign) SEL didStartSelector; + +// Called on the delegate (if implemented) when the request receives response headers. Default is request:didReceiveResponseHeaders: @property (assign) SEL didReceiveResponseHeadersSelector; + +// Called on the delegate (if implemented) when the request receives a Location header and shouldRedirect is YES +// The delegate can then change the url if needed, and can restart the request by calling [request redirectToURL:], or simply cancel it @property (assign) SEL willRedirectSelector; + +// Called on the delegate (if implemented) when the request completes successfully. Default is requestFinished: @property (assign) SEL didFinishSelector; + +// Called on the delegate (if implemented) when the request fails. Default is requestFailed: @property (assign) SEL didFailSelector; + +// Called on the delegate (if implemented) when the request receives data. Default is request:didReceiveData: +// If you set this and implement the method in your delegate, you must handle the data yourself - ASIHTTPRequest will not populate responseData or write the data to downloadDestinationPath @property (assign) SEL didReceiveDataSelector; + +// Realm for authentication when credentials are required @property (retain,readonly) NSString *authenticationRealm; -@property (retain,readonly) NSString *proxyAuthenticationRealm; -@property (retain) NSError *error; + +// Realm for proxy authentication when credentials are required +@property (strong,readonly) NSString *proxyAuthenticationRealm; + +// If an error occurs, error will contain an NSError +// If error code is = ASIConnectionFailureErrorType (1, Connection failure occurred) - inspect [[error userInfo] objectForKey:NSUnderlyingErrorKey] for more information +@property (strong) NSError *error; + +// When the request fails or completes successfully, complete will be true @property (assign,readonly) BOOL complete; + +// Will be populated with HTTP response headers from the server @property (retain) NSDictionary *responseHeaders; + +// Dictionary for custom HTTP request headers @property (retain) NSMutableDictionary *requestHeaders; -@property (retain) NSMutableArray *requestCookies; + +// Can be used to manually insert cookie headers to a request, but it's more likely that sessionCookies will do this for you +@property (strong) NSMutableArray *requestCookies; + +// Will be populated with cookies @property (retain,readonly) NSArray *responseCookies; + +// If use useCookiePersistence is true, network requests will present valid cookies from previous requests @property (assign) BOOL useCookiePersistence; + +// Used for authentication @property (retain) NSDictionary *requestCredentials; + +// Used for proxy authentication @property (retain) NSDictionary *proxyCredentials; @property (assign,readonly) int responseStatusCode; + +// Description of the HTTP status code @property (retain,readonly) NSString *responseStatusMessage; + + +// Data we receive will be stored here. Data may be compressed unless allowCompressedResponse is false - you should use [request responseData] instead in most cases @property (retain) NSMutableData *rawResponseData; + +// Number of seconds to wait before timing out - default is 10 @property (assign) NSTimeInterval timeOutSeconds; + +// HTTP method to use (eg: GET / POST / PUT / DELETE / HEAD etc). Defaults to GET @property (retain, nonatomic) NSString *requestMethod; -@property (retain) NSMutableData *postBody; + +// Request body - only used when the whole body is stored in memory (shouldStreamPostDataFromDisk is false) +@property (strong) NSMutableData *postBody; + +// Size of the response @property (assign) unsigned long long contentLength; @property (assign) unsigned long long postLength; + +// Will be YES when a HEAD request will handle the content-length before this request starts @property (assign) BOOL shouldResetDownloadProgress; @property (assign) BOOL shouldResetUploadProgress; -@property (assign) ASIHTTPRequest *mainRequest; + +// Used by HEAD requests when showAccurateProgress is YES to preset the content-length for this request +@property (weak) ASIHTTPRequest *mainRequest; + +// When NO, this request will only update the progress indicator when it completes +// When YES, this request will update the progress indicator according to how much data it has received so far +// The default for requests is YES +// Also see the comments in ASINetworkQueue.h @property (assign) BOOL showAccurateProgress; + +// The total amount of downloaded data @property (assign) unsigned long long totalBytesRead; + +// The total amount of uploaded data @property (assign) unsigned long long totalBytesSent; + +// Text encoding for responses that do not send a Content-Type with a charset value. Defaults to NSISOLatin1StringEncoding @property (assign) NSStringEncoding defaultResponseEncoding; @property (assign) NSStringEncoding responseEncoding; + +// If allowCompressedResponse is true, requests will inform the server they can accept compressed data, and will automatically decompress gzipped responses. Default is true. @property (assign) BOOL allowCompressedResponse; @property (assign) BOOL allowResumeForFileDownloads; -@property (retain) NSDictionary *userInfo; + +// Custom user information associated with the request (not sent to the server) +@property (strong) NSDictionary *userInfo; @property (assign) NSInteger tag; -@property (retain) NSString *postBodyFilePath; + +// Path to file used to store post body (when shouldStreamPostDataFromDisk is true) +// You can set this yourself - useful if you want to PUT a file from local disk +@property (strong) NSString *postBodyFilePath; + +// When true, post body will be streamed from a file on disk, rather than loaded into memory at once (useful for large uploads) +// Automatically set to true in ASIFormDataRequests when using setFile:forKey: @property (assign) BOOL shouldStreamPostDataFromDisk; + +// Set to true when ASIHTTPRequest automatically created a temporary file containing the request body (when true, the file at postBodyFilePath will be deleted at the end of the request) @property (assign) BOOL didCreateTemporaryPostDataFile; @property (assign) BOOL useHTTPVersionOne; @property (assign, readonly) unsigned long long partialDownloadSize; + +// When YES, requests will automatically redirect when they get a HTTP 30x header (defaults to YES) @property (assign) BOOL shouldRedirect; + +// When NO, requests will not check the secure certificate is valid (use for self-signed certificates during development, DO NOT USE IN PRODUCTION) Default is YES @property (assign) BOOL validatesSecureCertificate; + +// If shouldCompressRequestBody is true, the request body will be gzipped. Default is false. +// You will probably need to enable this feature on your webserver to make this work. Tested with apache only. @property (assign) BOOL shouldCompressRequestBody; + +// URL for a PAC (Proxy Auto Configuration) file. If you want to set this yourself, it's probably best if you use a local file @property (retain) NSURL *PACurl; + +// Authentication scheme (Basic, Digest, NTLM) +// If you are using Basic authentication and want to force ASIHTTPRequest to send an authorization header without waiting for a 401, you must set this to (NSString *)kCFHTTPAuthenticationSchemeBasic @property (retain) NSString *authenticationScheme; + +// Authentication scheme for the proxy (Basic, Digest, NTLM) @property (retain) NSString *proxyAuthenticationScheme; @property (assign) BOOL shouldPresentAuthenticationDialog; + +// When YES, ASIHTTPRequest will present a dialog allowing users to enter credentials when no-matching credentials were found for a proxy server that requires authentication +// The dialog will not be shown if your delegate responds to proxyAuthenticationNeededForRequest: +// Default is YES (basically, because most people won't want the hassle of adding support for authenticating proxies to their apps) @property (assign) BOOL shouldPresentProxyAuthenticationDialog; @property (assign, readonly) ASIAuthenticationState authenticationNeeded; + +// When YES, ASIHTTPRequests will present credentials from the session store for requests to the same server before being asked for them +// This avoids an extra round trip for requests after authentication has succeeded, which is much for efficient for authenticated requests with large bodies, or on slower connections +// Set to NO to only present credentials when explicitly asked for them +// This only affects credentials stored in the session cache when useSessionPersistence is YES. Credentials from the keychain are never presented unless the server asks for them +// Default is YES +// For requests using Basic authentication, set authenticationScheme to (NSString *)kCFHTTPAuthenticationSchemeBasic, and credentials can be sent on the very first request when shouldPresentCredentialsBeforeChallenge is YES @property (assign) BOOL shouldPresentCredentialsBeforeChallenge; @property (assign, readonly) int authenticationRetryCount; @property (assign, readonly) int proxyAuthenticationRetryCount; @property (assign) BOOL haveBuiltRequestHeaders; + +// Prevents the body of the post being built more than once (largely for subclasses) @property (assign, nonatomic) BOOL haveBuiltPostBody; @property (assign, readonly) BOOL inProgress; @property (assign) int numberOfTimesToRetryOnTimeout; @property (assign, readonly) int retryCount; + +// When YES, requests will keep the connection to the server alive for a while to allow subsequent requests to re-use it for a substantial speed-boost +// Persistent connections will not be used if the server explicitly closes the connection +// Default is YES @property (assign) BOOL shouldAttemptPersistentConnection; + +// Number of seconds to keep an inactive persistent connection open on the client side +// Default is 60 +// If we get a keep-alive header, this is this value is replaced with how long the server told us to keep the connection around +// A future date is created from this and used for expiring the connection, this is stored in connectionInfo's expires value @property (assign) NSTimeInterval persistentConnectionTimeoutSeconds; @property (assign) BOOL shouldUseRFC2616RedirectBehaviour; @property (assign, readonly) BOOL connectionCanBeReused; + +// An ID that uniquely identifies this request - primarily used for debugging persistent connections @property (retain, readonly) NSNumber *requestID; -@property (assign) id downloadCache; + +// The download cache that will be used for this request (use [ASIHTTPRequest setDefaultCache:cache] to configure a default cache +// id +@property (weak) id downloadCache; @property (assign) ASICachePolicy cachePolicy; @property (assign) ASICacheStoragePolicy cacheStoragePolicy; @property (assign, readonly) BOOL didUseCachedResponse; @property (assign) NSTimeInterval secondsToCache; + +// If not nil and the URL scheme is https, CFNetwork configured to supply a client certificate @property (retain) NSArray *clientCertificates; #if TARGET_OS_IPHONE && __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_4_0 @property (assign) BOOL shouldContinueWhenAppEntersBackground; #endif + +// When downloading a gzipped response, the request will use this helper object to inflate the response @property (retain) ASIDataDecompressor *dataDecompressor; + +// Controls how responses with a gzipped encoding are inflated (decompressed) +// When set to YES (This is the default): +// * gzipped responses for requests without a downloadDestinationPath will be inflated only when [request responseData] / [request responseString] is called +// * gzipped responses for requests with a downloadDestinationPath set will be inflated only when the request completes +// +// When set to NO +// All requests will inflate the response as it comes in +// * If the request has no downloadDestinationPath set, the raw (compressed) response is discarded and rawResponseData will contain the decompressed response +// * If the request has a downloadDestinationPath, the raw response will be stored in temporaryFileDownloadPath as normal, the inflated response will be stored in temporaryUncompressedDataDownloadPath +// Once the request completes successfully, the contents of temporaryUncompressedDataDownloadPath are moved into downloadDestinationPath +// +// Setting this to NO may be especially useful for users using ASIHTTPRequest in conjunction with a streaming parser, as it will allow partial gzipped responses to be inflated and passed on to the parser while the request is still running @property (assign) BOOL shouldWaitToInflateCompressedResponses; @end diff --git a/Classes/ASIHTTPRequest.m b/Classes/ASIHTTPRequest.m index 31756d2b..c23a4d38 100644 --- a/Classes/ASIHTTPRequest.m +++ b/Classes/ASIHTTPRequest.m @@ -13,7 +13,7 @@ #import "ASIHTTPRequest.h" #if TARGET_OS_IPHONE -#import "Reachability.h" +#import "_Reachability.h" #import "ASIAuthenticationDialog.h" #import #else @@ -23,8 +23,16 @@ #import "ASIDataDecompressor.h" #import "ASIDataCompressor.h" +#define ASISuppressPerformSelectorLeakWarning(Stuff) \ +do { \ +_Pragma("clang diagnostic push") \ +_Pragma("clang diagnostic ignored \"-Warc-performSelector-leaks\"") \ +Stuff \ +_Pragma("clang diagnostic pop") \ +} while (0) + // Automatically set on build -NSString *ASIHTTPRequestVersion = @"v1.8.1-61 2011-09-19"; +NSString *ASIHTTPRequestVersion = @"v1.8.1-126 2014-06-04"; static NSString *defaultUserAgent = nil; @@ -51,7 +59,7 @@ static NSTimeInterval defaultTimeOutSeconds = 10; static void ReadStreamClientCallBack(CFReadStreamRef readStream, CFStreamEventType type, void *clientCallBackInfo) { - [((ASIHTTPRequest*)clientCallBackInfo) handleNetworkEvent: type]; + [((__bridge ASIHTTPRequest*)clientCallBackInfo) handleNetworkEvent: type]; } // This lock prevents the operation from being cancelled while it is trying to update the progress, and vice versa @@ -138,7 +146,13 @@ static void ReadStreamClientCallBack(CFReadStreamRef readStream, CFStreamEventTy static NSOperationQueue *sharedQueue = nil; // Private stuff -@interface ASIHTTPRequest () +@interface ASIHTTPRequest () { + NSURL *_url; + id _delegate; + id _queue; + + NSString *_requestMethod; +} - (void)cancelLoad; @@ -166,7 +180,7 @@ - (BOOL)shouldTimeOut; - (BOOL)willRedirect; - (BOOL)willAskDelegateToConfirmRedirect; -+ (void)performInvocation:(NSInvocation *)invocation onTarget:(id *)target releasingObject:(id)objectToRelease; ++ (void)performInvocation:(NSInvocation *)invocation onTarget:(id)target releasingObject:(id)objectToRelease; + (void)hideNetworkActivityIndicatorAfterDelay; + (void)hideNetworkActivityIndicatorIfNeeeded; + (void)runRequests; @@ -200,46 +214,93 @@ - (void)callBlock:(ASIBasicBlock)block; - +// When the request fails or completes successfully, complete will be true @property (assign) BOOL complete; + +// Will be populated with cookies @property (retain) NSArray *responseCookies; @property (assign) int responseStatusCode; + +// Used for recording when something last happened during the request, we will compare this value with the current date to time out requests when appropriate @property (retain, nonatomic) NSDate *lastActivityTime; @property (assign) unsigned long long partialDownloadSize; @property (assign, nonatomic) unsigned long long uploadBufferSize; -@property (retain, nonatomic) NSOutputStream *postBodyWriteStream; + +// Used when writing to the post body when shouldStreamPostDataFromDisk is true (via appendPostData: or appendPostDataFromFile:) +@property (strong, nonatomic) NSOutputStream *postBodyWriteStream; + +// Used for reading from the post body when sending the request @property (retain, nonatomic) NSInputStream *postBodyReadStream; @property (assign, nonatomic) unsigned long long lastBytesRead; @property (assign, nonatomic) unsigned long long lastBytesSent; + +// This lock prevents the operation from being cancelled at an inopportune moment @property (retain) NSRecursiveLock *cancelledLock; + +// Used for writing data to a file when downloadDestinationPath is set @property (retain, nonatomic) NSOutputStream *fileDownloadOutputStream; @property (retain, nonatomic) NSOutputStream *inflatedFileDownloadOutputStream; + @property (assign) int authenticationRetryCount; @property (assign) int proxyAuthenticationRetryCount; @property (assign, nonatomic) BOOL updatedProgress; + +// Used internally to tell the main loop we need to stop and retry with a new url @property (assign, nonatomic) BOOL needsRedirect; @property (assign, nonatomic) int redirectCount; -@property (retain, nonatomic) NSData *compressedPostBody; -@property (retain, nonatomic) NSString *compressedPostBodyFilePath; + +// gzipped request body used when shouldCompressRequestBody is YES +@property (strong, nonatomic) NSData *compressedPostBody; + +// Path to a temporary file used to store a deflated post body (when shouldCompressPostBody is YES) +@property (strong, nonatomic) NSString *compressedPostBodyFilePath; @property (retain) NSString *authenticationRealm; -@property (retain) NSString *proxyAuthenticationRealm; + +// Realm for proxy authentication when credentials are required +@property (strong) NSString *proxyAuthenticationRealm; + +// Description of the HTTP status code @property (retain) NSString *responseStatusMessage; @property (assign) BOOL inProgress; @property (assign) int retryCount; @property (assign) BOOL willRetryRequest; @property (assign) BOOL connectionCanBeReused; + +// Stores information about the persistent connection that is currently in use. +// It may contain: +// * The id we set for a particular connection, incremented every time we want to specify that we need a new connection +// * The date that connection should expire +// * A host, port and scheme for the connection. These are used to determine whether that connection can be reused by a subsequent request (all must match the new request) +// * An id for the request that is currently using the connection. This is used for determining if a connection is available or not (we store a number rather than a reference to the request so we don't need to hang onto a request until the connection expires) +// * A reference to the stream that is currently using the connection. This is necessary because we need to keep the old stream open until we've opened a new one. +// The stream will be closed + released either when another request comes to use the connection, or when the timer fires to tell the connection to expire @property (retain, nonatomic) NSMutableDictionary *connectionInfo; + +// Used for sending and receiving data @property (retain, nonatomic) NSInputStream *readStream; @property (assign) ASIAuthenticationState authenticationNeeded; + +// Used internally to track whether the stream is scheduled on the run loop or not +// Bandwidth throttling can unschedule the stream to slow things down while a request is in progress @property (assign, nonatomic) BOOL readStreamIsScheduled; @property (assign, nonatomic) BOOL downloadComplete; + +// An ID that uniquely identifies this request - primarily used for debugging persistent connections @property (retain) NSNumber *requestID; -@property (assign, nonatomic) NSString *runLoopMode; -@property (retain, nonatomic) NSTimer *statusTimer; + +// Will be ASIHTTPRequestRunLoopMode for synchronous requests, NSDefaultRunLoopMode for all other requests +@property (strong, nonatomic) NSString *runLoopMode; + + +// This timer checks up on the request every 0.25 seconds, and updates progress +@property (strong, nonatomic) NSTimer *statusTimer; @property (assign) BOOL didUseCachedResponse; + +// Temporarily stores the url we are about to redirect to. Will be nil again when we do redirect @property (retain, nonatomic) NSURL *redirectURL; +// Will be YES if this is a request created behind the scenes to download a PAC file - these requests do not attempt to configure their own proxies @property (assign, nonatomic) BOOL isPACFileRequest; @property (retain, nonatomic) ASIHTTPRequest *PACFileRequest; @property (retain, nonatomic) NSInputStream *PACFileReadStream; @@ -264,11 +325,11 @@ + (void)initialize sessionCredentialsLock = [[NSRecursiveLock alloc] init]; delegateAuthenticationLock = [[NSRecursiveLock alloc] init]; bandwidthUsageTracker = [[NSMutableArray alloc] initWithCapacity:5]; - ASIRequestTimedOutError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASIRequestTimedOutErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:@"The request timed out",NSLocalizedDescriptionKey,nil]]; - ASIAuthenticationError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASIAuthenticationErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:@"Authentication needed",NSLocalizedDescriptionKey,nil]]; - ASIRequestCancelledError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASIRequestCancelledErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:@"The request was cancelled",NSLocalizedDescriptionKey,nil]]; - ASIUnableToCreateRequestError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASIUnableToCreateRequestErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:@"Unable to create request (bad url?)",NSLocalizedDescriptionKey,nil]]; - ASITooMuchRedirectionError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASITooMuchRedirectionErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:@"The request failed because it redirected too many times",NSLocalizedDescriptionKey,nil]]; + ASIRequestTimedOutError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASIRequestTimedOutErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:NSLocalizedStringFromTable(@"The request timed out", @"ASIHTTPLocalizable", @"The request timed out") ,NSLocalizedDescriptionKey,nil]]; + ASIAuthenticationError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASIAuthenticationErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:NSLocalizedStringFromTable(@"Authentication needed", @"ASIHTTPLocalizable", @"Authentication needed"),NSLocalizedDescriptionKey,nil]]; + ASIRequestCancelledError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASIRequestCancelledErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:NSLocalizedStringFromTable(@"The request was cancelled", @"ASIHTTPLocalizable", @"The request was cancelled"),NSLocalizedDescriptionKey,nil]]; + ASIUnableToCreateRequestError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASIUnableToCreateRequestErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:NSLocalizedStringFromTable(@"Unable to create request (bad url?)", @"ASIHTTPLocalizable", @"Unable to create request (bad url?)"),NSLocalizedDescriptionKey,nil]]; + ASITooMuchRedirectionError = [[NSError alloc] initWithDomain:NetworkRequestErrorDomain code:ASITooMuchRedirectionErrorType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:NSLocalizedStringFromTable(@"The request failed because it redirected too many times", @"ASIHTTPLocalizable", @"The request failed because it redirected too many times"),NSLocalizedDescriptionKey,nil]]; sharedQueue = [[NSOperationQueue alloc] init]; [sharedQueue setMaxConcurrentOperationCount:4]; @@ -276,7 +337,7 @@ + (void)initialize } -- (id)initWithURL:(NSURL *)newURL +- (instancetype)initWithURL:(NSURL *)newURL { self = [self init]; [self setRequestMethod:@"GET"]; @@ -298,7 +359,7 @@ - (id)initWithURL:(NSURL *)newURL [self setUseSessionPersistence:YES]; [self setUseCookiePersistence:YES]; [self setValidatesSecureCertificate:YES]; - [self setRequestCookies:[[[NSMutableArray alloc] init] autorelease]]; + [self setRequestCookies:[NSMutableArray array]]; [self setDidStartSelector:@selector(requestStarted:)]; [self setDidReceiveResponseHeadersSelector:@selector(request:didReceiveResponseHeaders:)]; [self setWillRedirectSelector:@selector(request:willRedirectToURL:)]; @@ -306,24 +367,24 @@ - (id)initWithURL:(NSURL *)newURL [self setDidFailSelector:@selector(requestFailed:)]; [self setDidReceiveDataSelector:@selector(request:didReceiveData:)]; [self setURL:newURL]; - [self setCancelledLock:[[[NSRecursiveLock alloc] init] autorelease]]; + [self setCancelledLock:[[NSRecursiveLock alloc] init]]; [self setDownloadCache:[[self class] defaultCache]]; return self; } -+ (id)requestWithURL:(NSURL *)newURL ++ (instancetype)requestWithURL:(NSURL *)newURL { - return [[[self alloc] initWithURL:newURL] autorelease]; + return [[self alloc] initWithURL:newURL]; } -+ (id)requestWithURL:(NSURL *)newURL usingCache:(id )cache ++ (instancetype)requestWithURL:(NSURL *)newURL usingCache:(id )cache { return [self requestWithURL:newURL usingCache:cache andCachePolicy:ASIUseDefaultCachePolicy]; } -+ (id)requestWithURL:(NSURL *)newURL usingCache:(id )cache andCachePolicy:(ASICachePolicy)policy ++ (instancetype)requestWithURL:(NSURL *)newURL usingCache:(id )cache andCachePolicy:(ASICachePolicy)policy { - ASIHTTPRequest *request = [[[self alloc] initWithURL:newURL] autorelease]; + ASIHTTPRequest *request = [[self alloc] initWithURL:newURL]; [request setDownloadCache:cache]; [request setCachePolicy:policy]; return request; @@ -345,60 +406,10 @@ - (void)dealloc CFRelease(clientCertificateIdentity); } [self cancelLoad]; - [redirectURL release]; - [statusTimer invalidate]; - [statusTimer release]; - [queue release]; - [userInfo release]; - [postBody release]; - [compressedPostBody release]; - [error release]; - [requestHeaders release]; - [requestCookies release]; - [downloadDestinationPath release]; - [temporaryFileDownloadPath release]; - [temporaryUncompressedDataDownloadPath release]; - [fileDownloadOutputStream release]; - [inflatedFileDownloadOutputStream release]; - [username release]; - [password release]; - [domain release]; - [authenticationRealm release]; - [authenticationScheme release]; - [requestCredentials release]; - [proxyHost release]; - [proxyType release]; - [proxyUsername release]; - [proxyPassword release]; - [proxyDomain release]; - [proxyAuthenticationRealm release]; - [proxyAuthenticationScheme release]; - [proxyCredentials release]; - [url release]; - [originalURL release]; - [lastActivityTime release]; - [responseCookies release]; - [rawResponseData release]; - [responseHeaders release]; - [requestMethod release]; - [cancelledLock release]; - [postBodyFilePath release]; - [compressedPostBodyFilePath release]; - [postBodyWriteStream release]; - [postBodyReadStream release]; - [PACurl release]; - [clientCertificates release]; - [responseStatusMessage release]; - [connectionInfo release]; - [requestID release]; - [dataDecompressor release]; - [userAgentString release]; - + [_statusTimer invalidate]; #if NS_BLOCKS_AVAILABLE [self releaseBlocksOnMainThread]; #endif - - [super dealloc]; } #if NS_BLOCKS_AVAILABLE @@ -407,62 +418,50 @@ - (void)releaseBlocksOnMainThread NSMutableArray *blocks = [NSMutableArray array]; if (completionBlock) { [blocks addObject:completionBlock]; - [completionBlock release]; completionBlock = nil; } if (failureBlock) { [blocks addObject:failureBlock]; - [failureBlock release]; failureBlock = nil; } if (startedBlock) { [blocks addObject:startedBlock]; - [startedBlock release]; startedBlock = nil; } if (headersReceivedBlock) { [blocks addObject:headersReceivedBlock]; - [headersReceivedBlock release]; headersReceivedBlock = nil; } if (bytesReceivedBlock) { [blocks addObject:bytesReceivedBlock]; - [bytesReceivedBlock release]; bytesReceivedBlock = nil; } if (bytesSentBlock) { [blocks addObject:bytesSentBlock]; - [bytesSentBlock release]; bytesSentBlock = nil; } if (downloadSizeIncrementedBlock) { [blocks addObject:downloadSizeIncrementedBlock]; - [downloadSizeIncrementedBlock release]; downloadSizeIncrementedBlock = nil; } if (uploadSizeIncrementedBlock) { [blocks addObject:uploadSizeIncrementedBlock]; - [uploadSizeIncrementedBlock release]; uploadSizeIncrementedBlock = nil; } if (dataReceivedBlock) { [blocks addObject:dataReceivedBlock]; - [dataReceivedBlock release]; dataReceivedBlock = nil; } if (proxyAuthenticationNeededBlock) { [blocks addObject:proxyAuthenticationNeededBlock]; - [proxyAuthenticationNeededBlock release]; proxyAuthenticationNeededBlock = nil; } if (authenticationNeededBlock) { [blocks addObject:authenticationNeededBlock]; - [authenticationNeededBlock release]; authenticationNeededBlock = nil; } if (requestRedirectedBlock) { [blocks addObject:requestRedirectedBlock]; - [requestRedirectedBlock release]; requestRedirectedBlock = nil; } [[self class] performSelectorOnMainThread:@selector(releaseBlocks:) withObject:blocks waitUntilDone:[NSThread isMainThread]]; @@ -479,10 +478,10 @@ + (void)releaseBlocks:(NSArray *)blocks - (void)addRequestHeader:(NSString *)header value:(NSString *)value { - if (!requestHeaders) { + if (!_requestHeaders) { [self setRequestHeaders:[NSMutableDictionary dictionaryWithCapacity:1]]; } - [requestHeaders setObject:value forKey:header]; + [_requestHeaders setObject:value forKey:header]; } // This function will be called either just before a request starts, or when postLength is needed, whichever comes first @@ -520,9 +519,9 @@ - (void)buildPostBody path = [self postBodyFilePath]; } NSError *err = nil; - [self setPostLength:[[[[[NSFileManager alloc] init] autorelease] attributesOfItemAtPath:path error:&err] fileSize]]; + [self setPostLength:[[[[NSFileManager alloc] init] attributesOfItemAtPath:path error:&err] fileSize]]; if (err) { - [self failWithError:[NSError errorWithDomain:NetworkRequestErrorDomain code:ASIFileManagementError userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"Failed to get attributes for file at path '%@'",path],NSLocalizedDescriptionKey,error,NSUnderlyingErrorKey,nil]]]; + [self failWithError:[NSError errorWithDomain:NetworkRequestErrorDomain code:ASIFileManagementError userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"Failed to get attributes for file at path '%@'",path],NSLocalizedDescriptionKey,_error,NSUnderlyingErrorKey,nil]]]; return; } @@ -543,7 +542,7 @@ - (void)buildPostBody } if ([self postLength] > 0) { - if ([requestMethod isEqualToString:@"GET"] || [requestMethod isEqualToString:@"DELETE"] || [requestMethod isEqualToString:@"HEAD"]) { + if ([[self requestMethod] isEqualToString:@"GET"] || [[self requestMethod] isEqualToString:@"DELETE"] || [[self requestMethod] isEqualToString:@"HEAD"]) { [self setRequestMethod:@"POST"]; } [self addRequestHeader:@"Content-Length" value:[NSString stringWithFormat:@"%llu",[self postLength]]]; @@ -561,12 +560,12 @@ - (void)setupPostBody [self setDidCreateTemporaryPostDataFile:YES]; } if (![self postBodyWriteStream]) { - [self setPostBodyWriteStream:[[[NSOutputStream alloc] initToFileAtPath:[self postBodyFilePath] append:NO] autorelease]]; + [self setPostBodyWriteStream:[[NSOutputStream alloc] initToFileAtPath:[self postBodyFilePath] append:NO]]; [[self postBodyWriteStream] open]; } } else { if (![self postBody]) { - [self setPostBody:[[[NSMutableData alloc] init] autorelease]]; + [self setPostBody:[[NSMutableData alloc] init]]; } } } @@ -587,7 +586,7 @@ - (void)appendPostData:(NSData *)data - (void)appendPostDataFromFile:(NSString *)file { [self setupPostBody]; - NSInputStream *stream = [[[NSInputStream alloc] initWithFileAtPath:file] autorelease]; + NSInputStream *stream = [[NSInputStream alloc] initWithFileAtPath:file]; [stream open]; NSUInteger bytesRead; while ([stream hasBytesAvailable]) { @@ -609,7 +608,7 @@ - (void)appendPostDataFromFile:(NSString *)file - (NSString *)requestMethod { [[self cancelledLock] lock]; - NSString *m = requestMethod; + NSString *m = _requestMethod; [[self cancelledLock] unlock]; return m; } @@ -617,10 +616,9 @@ - (NSString *)requestMethod - (void)setRequestMethod:(NSString *)newRequestMethod { [[self cancelledLock] lock]; - if (requestMethod != newRequestMethod) { - [requestMethod release]; - requestMethod = [newRequestMethod retain]; - if ([requestMethod isEqualToString:@"POST"] || [requestMethod isEqualToString:@"PUT"] || [postBody length] || postBodyFilePath) { + if (_requestMethod != newRequestMethod) { + _requestMethod = newRequestMethod; + if ([_requestMethod isEqualToString:@"POST"] || [_requestMethod isEqualToString:@"PUT"] || [_postBody length] || _postBodyFilePath) { [self setShouldAttemptPersistentConnection:NO]; } } @@ -630,7 +628,7 @@ - (void)setRequestMethod:(NSString *)newRequestMethod - (NSURL *)url { [[self cancelledLock] lock]; - NSURL *u = url; + NSURL *u = _url; [[self cancelledLock] unlock]; return u; } @@ -643,8 +641,7 @@ - (void)setURL:(NSURL *)newURL [[self cancelledLock] unlock]; return; } - [url release]; - url = [newURL retain]; + _url = newURL; if (requestAuthentication) { CFRelease(requestAuthentication); requestAuthentication = NULL; @@ -664,7 +661,7 @@ - (void)setURL:(NSURL *)newURL - (id)delegate { [[self cancelledLock] lock]; - id d = delegate; + id d = _delegate; [[self cancelledLock] unlock]; return d; } @@ -672,14 +669,14 @@ - (id)delegate - (void)setDelegate:(id)newDelegate { [[self cancelledLock] lock]; - delegate = newDelegate; + _delegate = newDelegate; [[self cancelledLock] unlock]; } - (id)queue { [[self cancelledLock] lock]; - id q = queue; + id q = _queue; [[self cancelledLock] unlock]; return q; } @@ -688,9 +685,8 @@ - (id)queue - (void)setQueue:(id)newQueue { [[self cancelledLock] lock]; - if (newQueue != queue) { - [queue release]; - queue = [newQueue retain]; + if (newQueue != _queue) { + _queue = newQueue; } [[self cancelledLock] unlock]; } @@ -714,13 +710,13 @@ - (void)cancelOnRequestThread [self setComplete:YES]; [self cancelLoad]; - CFRetain(self); + CFRetain((__bridge CFTypeRef)(self)); [self willChangeValueForKey:@"isCancelled"]; cancelled = YES; [self didChangeValueForKey:@"isCancelled"]; [[self cancelledLock] unlock]; - CFRelease(self); + CFRelease((__bridge CFTypeRef)(self)); } - (void)cancel @@ -767,7 +763,7 @@ - (NSString *)responseString return nil; } - return [[[NSString alloc] initWithBytes:[data bytes] length:[data length] encoding:[self responseEncoding]] autorelease]; + return [[NSString alloc] initWithBytes:[data bytes] length:[data length] encoding:[self responseEncoding]]; } - (BOOL)isResponseCompressed @@ -799,7 +795,7 @@ - (void)startSynchronous if (![self isCancelled] && ![self complete]) { [self main]; - while (!complete) { + while (![self complete]) { [[NSRunLoop currentRunLoop] runMode:[self runLoopMode] beforeDate:[NSDate distantFuture]]; } } @@ -839,7 +835,7 @@ - (BOOL)isExecuting { #pragma mark request logic -// Create the request +// Create the requestImd - (void)main { @try { @@ -860,6 +856,14 @@ - (void)main [self cancel]; } }); + + UILocalNotification *localNotification = [[UILocalNotification alloc] init]; + + localNotification.fireDate = [NSDate date]; + localNotification.alertBody = NSLocalizedString(@"Upload was stopped by ios due to excceeding maximum background time.", @"Upload was stopped by ios due to excceeding maximum background time"); + localNotification.soundName = UILocalNotificationDefaultSoundName; + + [[UIApplication sharedApplication] scheduleLocalNotification:localNotification]; }]; } } @@ -897,7 +901,7 @@ - (void)main } // Create a new HTTP request. - request = CFHTTPMessageCreateRequest(kCFAllocatorDefault, (CFStringRef)[self requestMethod], (CFURLRef)[self url], [self useHTTPVersionOne] ? kCFHTTPVersion1_0 : kCFHTTPVersion1_1); + request = CFHTTPMessageCreateRequest(kCFAllocatorDefault, (__bridge CFStringRef)[self requestMethod], (__bridge CFURLRef)[self url], [self useHTTPVersionOne] ? kCFHTTPVersion1_0 : kCFHTTPVersion1_1); if (!request) { [self failWithError:ASIUnableToCreateRequestError]; return; @@ -946,7 +950,7 @@ - (void)main NSString *header; for (header in [self requestHeaders]) { - CFHTTPMessageSetHeaderFieldValue(request, (CFStringRef)header, (CFStringRef)[[self requestHeaders] objectForKey:header]); + CFHTTPMessageSetHeaderFieldValue(request, (__bridge CFStringRef)header, (__bridge CFStringRef)[[self requestHeaders] objectForKey:header]); } // If we immediately have access to proxy settings, start the request @@ -1000,7 +1004,7 @@ - (void)applyAuthorizationHeader if ([credentials objectForKey:@"Authentication"]) { // If we've already talked to this server and have valid credentials, let's apply them to the request - if (CFHTTPMessageApplyCredentialDictionary(request, (CFHTTPAuthenticationRef)[credentials objectForKey:@"Authentication"], (CFDictionaryRef)[credentials objectForKey:@"Credentials"], NULL)) { + if (CFHTTPMessageApplyCredentialDictionary(request, (__bridge CFHTTPAuthenticationRef)[credentials objectForKey:@"Authentication"], (__bridge CFDictionaryRef)[credentials objectForKey:@"Credentials"], NULL)) { [self setAuthenticationScheme:[credentials objectForKey:@"AuthenticationScheme"]]; #if DEBUG_HTTP_AUTHENTICATION ASI_DEBUG_LOG(@"[AUTH] Request %@ found cached credentials (%@), will reuse without waiting for an authentication challenge",self,[credentials objectForKey:@"AuthenticationScheme"]); @@ -1030,7 +1034,7 @@ - (void)applyAuthorizationHeader if ([self useSessionPersistence]) { credentials = [self findSessionProxyAuthenticationCredentials]; if (credentials) { - if (!CFHTTPMessageApplyCredentialDictionary(request, (CFHTTPAuthenticationRef)[credentials objectForKey:@"Authentication"], (CFDictionaryRef)[credentials objectForKey:@"Credentials"], NULL)) { + if (!CFHTTPMessageApplyCredentialDictionary(request, (__bridge CFHTTPAuthenticationRef)[credentials objectForKey:@"Authentication"], (__bridge CFDictionaryRef)[credentials objectForKey:@"Credentials"], NULL)) { [[self class] removeProxyAuthenticationCredentialsFromSessionStore:[credentials objectForKey:@"Credentials"]]; } } @@ -1117,13 +1121,13 @@ - (void)buildRequestHeaders - (void)updatePartialDownloadSize { - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; if ([self allowResumeForFileDownloads] && [self downloadDestinationPath] && [self temporaryFileDownloadPath] && [fileManager fileExistsAtPath:[self temporaryFileDownloadPath]]) { NSError *err = nil; [self setPartialDownloadSize:[[fileManager attributesOfItemAtPath:[self temporaryFileDownloadPath] error:&err] fileSize]]; if (err) { - [self failWithError:[NSError errorWithDomain:NetworkRequestErrorDomain code:ASIFileManagementError userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"Failed to get attributes for file at path '%@'",[self temporaryFileDownloadPath]],NSLocalizedDescriptionKey,error,NSUnderlyingErrorKey,nil]]]; + [self failWithError:[NSError errorWithDomain:NetworkRequestErrorDomain code:ASIFileManagementError userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"Failed to get attributes for file at path '%@'",[self temporaryFileDownloadPath]],NSLocalizedDescriptionKey,[self error],NSUnderlyingErrorKey,nil]]]; return; } } @@ -1155,7 +1159,7 @@ - (void)startRequest [self setContentLength:0]; [self setResponseHeaders:nil]; if (![self downloadDestinationPath]) { - [self setRawResponseData:[[[NSMutableData alloc] init] autorelease]]; + [self setRawResponseData:[NSMutableData data]]; } @@ -1163,7 +1167,7 @@ - (void)startRequest // Create the stream for the request // - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; [self setReadStreamIsScheduled:NO]; @@ -1172,24 +1176,24 @@ - (void)startRequest // Are we gzipping the request body? if ([self compressedPostBodyFilePath] && [fileManager fileExistsAtPath:[self compressedPostBodyFilePath]]) { - [self setPostBodyReadStream:[ASIInputStream inputStreamWithFileAtPath:[self compressedPostBodyFilePath] request:self]]; + [self setPostBodyReadStream:(NSInputStream *)[ASIInputStream inputStreamWithFileAtPath:[self compressedPostBodyFilePath] request:self]]; } else { - [self setPostBodyReadStream:[ASIInputStream inputStreamWithFileAtPath:[self postBodyFilePath] request:self]]; + [self setPostBodyReadStream:(NSInputStream *)[ASIInputStream inputStreamWithFileAtPath:[self postBodyFilePath] request:self]]; } - [self setReadStream:[NSMakeCollectable(CFReadStreamCreateForStreamedHTTPRequest(kCFAllocatorDefault, request,(CFReadStreamRef)[self postBodyReadStream])) autorelease]]; + [self setReadStream:(__bridge_transfer id)(CFReadStreamCreateForStreamedHTTPRequest(kCFAllocatorDefault, request,(__bridge CFReadStreamRef)[self postBodyReadStream]))]; } else { // If we have a request body, we'll stream it from memory using our custom stream, so that we can measure bandwidth use and it can be bandwidth-throttled if necessary if ([self postBody] && [[self postBody] length] > 0) { if ([self shouldCompressRequestBody] && [self compressedPostBody]) { - [self setPostBodyReadStream:[ASIInputStream inputStreamWithData:[self compressedPostBody] request:self]]; + [self setPostBodyReadStream:(NSInputStream *)[ASIInputStream inputStreamWithData:[self compressedPostBody] request:self]]; } else if ([self postBody]) { - [self setPostBodyReadStream:[ASIInputStream inputStreamWithData:[self postBody] request:self]]; + [self setPostBodyReadStream:(NSInputStream *)[ASIInputStream inputStreamWithData:[self postBody] request:self]]; } - [self setReadStream:[NSMakeCollectable(CFReadStreamCreateForStreamedHTTPRequest(kCFAllocatorDefault, request,(CFReadStreamRef)[self postBodyReadStream])) autorelease]]; + [self setReadStream:(__bridge_transfer id)(CFReadStreamCreateForStreamedHTTPRequest(kCFAllocatorDefault, request,(__bridge CFReadStreamRef)[self postBodyReadStream]))]; } else { - [self setReadStream:[NSMakeCollectable(CFReadStreamCreateForHTTPRequest(kCFAllocatorDefault, request)) autorelease]]; + [self setReadStream:(__bridge_transfer id)(CFReadStreamCreateForHTTPRequest(kCFAllocatorDefault, request))]; } } @@ -1207,42 +1211,41 @@ - (void)startRequest if([[[[self url] scheme] lowercaseString] isEqualToString:@"https"]) { + NSMutableDictionary *sslProperties = [[NSMutableDictionary alloc] init]; + // Tell CFNetwork not to validate SSL certificates if (![self validatesSecureCertificate]) { // see: http://iphonedevelopment.blogspot.com/2010/05/nsstream-tcp-and-ssl.html - NSDictionary *sslProperties = [[NSDictionary alloc] initWithObjectsAndKeys: - [NSNumber numberWithBool:YES], kCFStreamSSLAllowsExpiredCertificates, - [NSNumber numberWithBool:YES], kCFStreamSSLAllowsAnyRoot, - [NSNumber numberWithBool:NO], kCFStreamSSLValidatesCertificateChain, - kCFNull,kCFStreamSSLPeerName, - nil]; + [sslProperties setObject:[NSNumber numberWithBool:YES] forKey:(NSString*)kCFStreamSSLAllowsExpiredCertificates]; + [sslProperties setObject:[NSNumber numberWithBool:YES] forKey:(NSString*)kCFStreamSSLAllowsAnyRoot]; + [sslProperties setObject:[NSNumber numberWithBool:NO] forKey:(NSString*)kCFStreamSSLValidatesCertificateChain]; + [sslProperties setObject:(NSString*)kCFNull forKey:(NSString*)kCFStreamSSLPeerName]; - CFReadStreamSetProperty((CFReadStreamRef)[self readStream], - kCFStreamPropertySSLSettings, - (CFTypeRef)sslProperties); - [sslProperties release]; + CFReadStreamSetProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertySSLSettings, (__bridge CFTypeRef)sslProperties); } // Tell CFNetwork to use a client certificate if (clientCertificateIdentity) { - NSMutableDictionary *sslProperties = [NSMutableDictionary dictionaryWithCapacity:1]; - - NSMutableArray *certificates = [NSMutableArray arrayWithCapacity:[clientCertificates count]+1]; + NSMutableArray *certificates = [NSMutableArray arrayWithCapacity:[_clientCertificates count]+1]; // The first object in the array is our SecIdentityRef - [certificates addObject:(id)clientCertificateIdentity]; + [certificates addObject:(__bridge id)clientCertificateIdentity]; // If we've added any additional certificates, add them too - for (id cert in clientCertificates) { + for (id cert in _clientCertificates) { [certificates addObject:cert]; } [sslProperties setObject:certificates forKey:(NSString *)kCFStreamSSLCertificates]; - CFReadStreamSetProperty((CFReadStreamRef)[self readStream], kCFStreamPropertySSLSettings, sslProperties); + CFReadStreamSetProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertySSLSettings, (__bridge CFTypeRef)(sslProperties)); } + if ([[[UIDevice currentDevice] systemVersion] compare:@"5.0" options:NSNumericSearch] != NSOrderedAscending && [[[UIDevice currentDevice] systemVersion] compare:@"5.1" options:NSNumericSearch] == NSOrderedAscending) { + [sslProperties setObject:@"kCFStreamSocketSecurityLevelTLSv1_0SSLv3" forKey:(NSString*)kCFStreamSSLLevel]; + CFReadStreamSetProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertySSLSettings, (__bridge CFTypeRef) sslProperties); + } } // @@ -1271,9 +1274,9 @@ - (void)startRequest NSMutableDictionary *proxyToUse = [NSMutableDictionary dictionaryWithObjectsAndKeys:[self proxyHost],hostKey,[NSNumber numberWithInt:[self proxyPort]],portKey,nil]; if ([[self proxyType] isEqualToString:(NSString *)kCFProxyTypeSOCKS]) { - CFReadStreamSetProperty((CFReadStreamRef)[self readStream], kCFStreamPropertySOCKSProxy, proxyToUse); + CFReadStreamSetProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertySOCKSProxy, (__bridge CFTypeRef)(proxyToUse)); } else { - CFReadStreamSetProperty((CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPProxy, proxyToUse); + CFReadStreamSetProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPProxy, (__bridge CFTypeRef)(proxyToUse)); } } @@ -1335,8 +1338,8 @@ - (void)startRequest } if ([[self connectionInfo] objectForKey:@"stream"]) { - oldStream = [[[self connectionInfo] objectForKey:@"stream"] retain]; - + oldStream = [[self connectionInfo] objectForKey:@"stream"]; + CFRetain((__bridge CFTypeRef)oldStream); } // No free connection was found in the pool matching the server/scheme/port we're connecting to, we'll need to create a new one @@ -1357,7 +1360,7 @@ - (void)startRequest } [[self connectionInfo] setObject:[self requestID] forKey:@"request"]; [[self connectionInfo] setObject:[self readStream] forKey:@"stream"]; - CFReadStreamSetProperty((CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPAttemptPersistentConnection, kCFBooleanTrue); + CFReadStreamSetProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPAttemptPersistentConnection, kCFBooleanTrue); #if DEBUG_PERSISTENT_CONNECTIONS ASI_DEBUG_LOG(@"[CONNECTION] Request #%@ will use connection #%i",[self requestID],[[[self connectionInfo] objectForKey:@"id"] intValue]); @@ -1366,9 +1369,8 @@ - (void)startRequest // Tag the stream with an id that tells it which connection to use behind the scenes // See http://lists.apple.com/archives/macnetworkprog/2008/Dec/msg00001.html for details on this approach + CFReadStreamSetProperty((__bridge CFReadStreamRef)[self readStream], CFSTR("ASIStreamID"), (__bridge CFTypeRef)([[self connectionInfo] objectForKey:@"id"])); - CFReadStreamSetProperty((CFReadStreamRef)[self readStream], CFSTR("ASIStreamID"), [[self connectionInfo] objectForKey:@"id"]); - } else { #if DEBUG_PERSISTENT_CONNECTIONS ASI_DEBUG_LOG(@"[CONNECTION] Request %@ will not use a persistent connection",self); @@ -1386,9 +1388,9 @@ - (void)startRequest // Start the HTTP connection - CFStreamClientContext ctxt = {0, self, NULL, NULL, NULL}; - if (CFReadStreamSetClient((CFReadStreamRef)[self readStream], kNetworkEvents, ReadStreamClientCallBack, &ctxt)) { - if (CFReadStreamOpen((CFReadStreamRef)[self readStream])) { + CFStreamClientContext ctxt = {0, (__bridge void *)(self), NULL, NULL, NULL}; + if (CFReadStreamSetClient((__bridge CFReadStreamRef)[self readStream], kNetworkEvents, ReadStreamClientCallBack, &ctxt)) { + if (CFReadStreamOpen((__bridge CFReadStreamRef)[self readStream])) { streamSuccessfullyOpened = YES; } } @@ -1398,7 +1400,7 @@ - (void)startRequest // http://lists.apple.com/archives/Macnetworkprog/2006/Mar/msg00119.html if (oldStream) { [oldStream close]; - [oldStream release]; + CFRelease((__bridge CFTypeRef)oldStream); oldStream = nil; } @@ -1416,10 +1418,10 @@ - (void)startRequest } else { [self incrementUploadSizeBy:1]; } - [ASIHTTPRequest updateProgressIndicator:&uploadProgressDelegate withProgress:0 ofTotal:1]; + [ASIHTTPRequest updateProgressIndicator:_uploadProgressDelegate withProgress:0 ofTotal:1]; } if ([self shouldResetDownloadProgress] && ![self partialDownloadSize]) { - [ASIHTTPRequest updateProgressIndicator:&downloadProgressDelegate withProgress:0 ofTotal:1]; + [ASIHTTPRequest updateProgressIndicator:_downloadProgressDelegate withProgress:0 ofTotal:1]; } } @@ -1432,15 +1434,14 @@ - (void)startRequest - (void)setStatusTimer:(NSTimer *)timer { - CFRetain(self); + CFRetain((__bridge CFTypeRef)(self)); // We must invalidate the old timer here, not before we've created and scheduled a new timer // This is because the timer may be the only thing retaining an asynchronous request - if (statusTimer && timer != statusTimer) { - [statusTimer invalidate]; - [statusTimer release]; + if (_statusTimer && timer != _statusTimer) { + [_statusTimer invalidate]; } - statusTimer = [timer retain]; - CFRelease(self); + _statusTimer = timer; + CFRelease((__bridge CFTypeRef)(self)); } // This gets fired every 1/4 of a second to update the progress and work out if we need to timeout @@ -1478,7 +1479,7 @@ - (void)redirectToURL:(NSURL *)newURL - (BOOL)shouldTimeOut { - NSTimeInterval secondsSinceLastActivity = [[NSDate date] timeIntervalSinceDate:lastActivityTime]; + NSTimeInterval secondsSinceLastActivity = [[NSDate date] timeIntervalSinceDate:_lastActivityTime]; // See if we need to timeout if ([self readStream] && [self readStreamIsScheduled] && [self lastActivityTime] && [self timeOutSeconds] > 0 && secondsSinceLastActivity > [self timeOutSeconds]) { @@ -1515,7 +1516,7 @@ - (void)checkRequestStatus // If we are resuming a download, we may need to update the Range header to take account of data we've just downloaded [self updatePartialDownloadSize]; if ([self partialDownloadSize]) { - CFHTTPMessageSetHeaderFieldValue(request, (CFStringRef)@"Range", (CFStringRef)[NSString stringWithFormat:@"bytes=%llu-",[self partialDownloadSize]]); + CFHTTPMessageSetHeaderFieldValue(request, (__bridge CFStringRef)@"Range", (__bridge CFStringRef)[NSString stringWithFormat:@"bytes=%llu-",[self partialDownloadSize]]); } [self setRetryCount:[self retryCount]+1]; [self unscheduleReadStream]; @@ -1536,15 +1537,15 @@ - (void)checkRequestStatus // If we have a post body if ([self postLength]) { - [self setLastBytesSent:totalBytesSent]; + [self setLastBytesSent:_totalBytesSent]; // Find out how much data we've uploaded so far - [self setTotalBytesSent:[[NSMakeCollectable(CFReadStreamCopyProperty((CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPRequestBytesWrittenCount)) autorelease] unsignedLongLongValue]]; - if (totalBytesSent > lastBytesSent) { + [self setTotalBytesSent:[(__bridge_transfer id)(CFReadStreamCopyProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPRequestBytesWrittenCount)) unsignedLongLongValue]]; + if (_totalBytesSent > lastBytesSent) { // We've uploaded more data, reset the timeout [self setLastActivityTime:[NSDate date]]; - [ASIHTTPRequest incrementBandwidthUsedInLastSecond:(unsigned long)(totalBytesSent-lastBytesSent)]; + [ASIHTTPRequest incrementBandwidthUsedInLastSecond:(unsigned long)(_totalBytesSent-lastBytesSent)]; #if DEBUG_REQUEST_STATUS if ([self totalBytesSent] == [self postLength]) { @@ -1619,8 +1620,8 @@ - (ASIHTTPRequest *)HEADRequest ASIHTTPRequest *headRequest = [[self class] requestWithURL:[self url]]; // Copy the properties that make sense for a HEAD request - [headRequest setRequestHeaders:[[[self requestHeaders] mutableCopy] autorelease]]; - [headRequest setRequestCookies:[[[self requestCookies] mutableCopy] autorelease]]; + [headRequest setRequestHeaders:[[self requestHeaders] mutableCopy]]; + [headRequest setRequestCookies:[[self requestCookies] mutableCopy]]; [headRequest setUseCookiePersistence:[self useCookiePersistence]]; [headRequest setUseKeychainPersistence:[self useKeychainPersistence]]; [headRequest setUseSessionPersistence:[self useSessionPersistence]]; @@ -1640,7 +1641,7 @@ - (ASIHTTPRequest *)HEADRequest [headRequest setUseHTTPVersionOne:[self useHTTPVersionOne]]; [headRequest setValidatesSecureCertificate:[self validatesSecureCertificate]]; [headRequest setClientCertificateIdentity:clientCertificateIdentity]; - [headRequest setClientCertificates:[[clientCertificates copy] autorelease]]; + [headRequest setClientCertificates:[_clientCertificates copy]]; [headRequest setPACurl:[self PACurl]]; [headRequest setShouldPresentCredentialsBeforeChallenge:[self shouldPresentCredentialsBeforeChallenge]]; [headRequest setNumberOfTimesToRetryOnTimeout:[self numberOfTimesToRetryOnTimeout]]; @@ -1668,44 +1669,28 @@ - (void)updateProgressIndicators } } -- (id)uploadProgressDelegate -{ - [[self cancelledLock] lock]; - id d = [[uploadProgressDelegate retain] autorelease]; - [[self cancelledLock] unlock]; - return d; -} - - (void)setUploadProgressDelegate:(id)newDelegate { [[self cancelledLock] lock]; - uploadProgressDelegate = newDelegate; + _uploadProgressDelegate = newDelegate; #if !TARGET_OS_IPHONE // If the uploadProgressDelegate is an NSProgressIndicator, we set its MaxValue to 1.0 so we can update it as if it were a UIProgressView double max = 1.0; - [ASIHTTPRequest performSelector:@selector(setMaxValue:) onTarget:&uploadProgressDelegate withObject:nil amount:&max callerToRetain:nil]; + [ASIHTTPRequest performSelector:@selector(setMaxValue:) onTarget:&_uploadProgressDelegate withObject:nil amount:&max callerToRetain:nil]; #endif [[self cancelledLock] unlock]; } -- (id)downloadProgressDelegate -{ - [[self cancelledLock] lock]; - id d = [[downloadProgressDelegate retain] autorelease]; - [[self cancelledLock] unlock]; - return d; -} - - (void)setDownloadProgressDelegate:(id)newDelegate { [[self cancelledLock] lock]; - downloadProgressDelegate = newDelegate; + _downloadProgressDelegate = newDelegate; #if !TARGET_OS_IPHONE // If the downloadProgressDelegate is an NSProgressIndicator, we set its MaxValue to 1.0 so we can update it as if it were a UIProgressView double max = 1.0; - [ASIHTTPRequest performSelector:@selector(setMaxValue:) onTarget:&downloadProgressDelegate withObject:nil amount:&max callerToRetain:nil]; + [ASIHTTPRequest performSelector:@selector(setMaxValue:) onTarget:&_downloadProgressDelegate withObject:nil amount:&max callerToRetain:nil]; #endif [[self cancelledLock] unlock]; } @@ -1734,10 +1719,10 @@ - (void)updateDownloadProgress return; } - [ASIHTTPRequest performSelector:@selector(request:didReceiveBytes:) onTarget:&queue withObject:self amount:&value callerToRetain:self]; - [ASIHTTPRequest performSelector:@selector(request:didReceiveBytes:) onTarget:&downloadProgressDelegate withObject:self amount:&value callerToRetain:self]; + [ASIHTTPRequest performSelector:@selector(request:didReceiveBytes:) onTarget:_queue withObject:self amount:&value callerToRetain:self]; + [ASIHTTPRequest performSelector:@selector(request:didReceiveBytes:) onTarget:_downloadProgressDelegate withObject:self amount:&value callerToRetain:self]; - [ASIHTTPRequest updateProgressIndicator:&downloadProgressDelegate withProgress:[self totalBytesRead]+[self partialDownloadSize] ofTotal:[self contentLength]+[self partialDownloadSize]]; + [ASIHTTPRequest updateProgressIndicator:_downloadProgressDelegate withProgress:[self totalBytesRead]+[self partialDownloadSize] ofTotal:[self contentLength]+[self partialDownloadSize]]; #if NS_BLOCKS_AVAILABLE if (bytesReceivedBlock) { @@ -1779,9 +1764,9 @@ - (void)updateUploadProgress return; } - [ASIHTTPRequest performSelector:@selector(request:didSendBytes:) onTarget:&queue withObject:self amount:&value callerToRetain:self]; - [ASIHTTPRequest performSelector:@selector(request:didSendBytes:) onTarget:&uploadProgressDelegate withObject:self amount:&value callerToRetain:self]; - [ASIHTTPRequest updateProgressIndicator:&uploadProgressDelegate withProgress:[self totalBytesSent]-[self uploadBufferSize] ofTotal:[self postLength]-[self uploadBufferSize]]; + [ASIHTTPRequest performSelector:@selector(request:didSendBytes:) onTarget:_queue withObject:self amount:&value callerToRetain:self]; + [ASIHTTPRequest performSelector:@selector(request:didSendBytes:) onTarget:_uploadProgressDelegate withObject:self amount:&value callerToRetain:self]; + [ASIHTTPRequest updateProgressIndicator:_uploadProgressDelegate withProgress:[self totalBytesSent]-[self uploadBufferSize] ofTotal:[self postLength]-[self uploadBufferSize]]; #if NS_BLOCKS_AVAILABLE if(bytesSentBlock){ @@ -1794,8 +1779,8 @@ - (void)updateUploadProgress - (void)incrementDownloadSizeBy:(long long)length { - [ASIHTTPRequest performSelector:@selector(request:incrementDownloadSizeBy:) onTarget:&queue withObject:self amount:&length callerToRetain:self]; - [ASIHTTPRequest performSelector:@selector(request:incrementDownloadSizeBy:) onTarget:&downloadProgressDelegate withObject:self amount:&length callerToRetain:self]; + [ASIHTTPRequest performSelector:@selector(request:incrementDownloadSizeBy:) onTarget:_queue withObject:self amount:&length callerToRetain:self]; + [ASIHTTPRequest performSelector:@selector(request:incrementDownloadSizeBy:) onTarget:_downloadProgressDelegate withObject:self amount:&length callerToRetain:self]; #if NS_BLOCKS_AVAILABLE if(downloadSizeIncrementedBlock){ @@ -1806,8 +1791,8 @@ - (void)incrementDownloadSizeBy:(long long)length - (void)incrementUploadSizeBy:(long long)length { - [ASIHTTPRequest performSelector:@selector(request:incrementUploadSizeBy:) onTarget:&queue withObject:self amount:&length callerToRetain:self]; - [ASIHTTPRequest performSelector:@selector(request:incrementUploadSizeBy:) onTarget:&uploadProgressDelegate withObject:self amount:&length callerToRetain:self]; + [ASIHTTPRequest performSelector:@selector(request:incrementUploadSizeBy:) onTarget:_queue withObject:self amount:&length callerToRetain:self]; + [ASIHTTPRequest performSelector:@selector(request:incrementUploadSizeBy:) onTarget:_uploadProgressDelegate withObject:self amount:&length callerToRetain:self]; #if NS_BLOCKS_AVAILABLE if(uploadSizeIncrementedBlock) { @@ -1820,9 +1805,9 @@ - (void)incrementUploadSizeBy:(long long)length -(void)removeUploadProgressSoFar { long long progressToRemove = -[self totalBytesSent]; - [ASIHTTPRequest performSelector:@selector(request:didSendBytes:) onTarget:&queue withObject:self amount:&progressToRemove callerToRetain:self]; - [ASIHTTPRequest performSelector:@selector(request:didSendBytes:) onTarget:&uploadProgressDelegate withObject:self amount:&progressToRemove callerToRetain:self]; - [ASIHTTPRequest updateProgressIndicator:&uploadProgressDelegate withProgress:0 ofTotal:[self postLength]]; + [ASIHTTPRequest performSelector:@selector(request:didSendBytes:) onTarget:_queue withObject:self amount:&progressToRemove callerToRetain:self]; + [ASIHTTPRequest performSelector:@selector(request:didSendBytes:) onTarget:_uploadProgressDelegate withObject:self amount:&progressToRemove callerToRetain:self]; + [ASIHTTPRequest updateProgressIndicator:_uploadProgressDelegate withProgress:0 ofTotal:[self postLength]]; #if NS_BLOCKS_AVAILABLE if(bytesSentBlock){ @@ -1835,7 +1820,7 @@ -(void)removeUploadProgressSoFar #if NS_BLOCKS_AVAILABLE - (void)performBlockOnMainThread:(ASIBasicBlock)block { - [self performSelectorOnMainThread:@selector(callBlock:) withObject:[[block copy] autorelease] waitUntilDone:[NSThread isMainThread]]; + [self performSelectorOnMainThread:@selector(callBlock:) withObject:[block copy] waitUntilDone:[NSThread isMainThread]]; } - (void)callBlock:(ASIBasicBlock)block @@ -1845,11 +1830,11 @@ - (void)callBlock:(ASIBasicBlock)block #endif -+ (void)performSelector:(SEL)selector onTarget:(id *)target withObject:(id)object amount:(void *)amount callerToRetain:(id)callerToRetain ++ (void)performSelector:(SEL)selector onTarget:(id)target withObject:(id)object amount:(void *)amount callerToRetain:(id)callerToRetain { - if ([*target respondsToSelector:selector]) { + if ([target respondsToSelector:selector]) { NSMethodSignature *signature = nil; - signature = [*target methodSignatureForSelector:selector]; + signature = [target methodSignatureForSelector:selector]; NSInvocation *invocation = [NSInvocation invocationWithMethodSignature:signature]; [invocation setSelector:selector]; @@ -1878,30 +1863,30 @@ + (void)performSelector:(SEL)selector onTarget:(id *)target withObject:(id)objec [cbInvocation setArgument:&callerToRetain atIndex:4]; } - CFRetain(invocation); + CFRetain((__bridge CFTypeRef)(invocation)); // Used to pass in a request that we must retain until after the call // We're using CFRetain rather than [callerToRetain retain] so things to avoid earthquakes when using garbage collection if (callerToRetain) { - CFRetain(callerToRetain); + CFRetain((__bridge CFTypeRef)(callerToRetain)); } [cbInvocation performSelectorOnMainThread:@selector(invoke) withObject:nil waitUntilDone:[NSThread isMainThread]]; } } -+ (void)performInvocation:(NSInvocation *)invocation onTarget:(id *)target releasingObject:(id)objectToRelease ++ (void)performInvocation:(NSInvocation *)invocation onTarget:(id)target releasingObject:(id)objectToRelease { - if (*target && [*target respondsToSelector:[invocation selector]]) { - [invocation invokeWithTarget:*target]; + if (target && [target respondsToSelector:[invocation selector]]) { + [invocation invokeWithTarget:target]; } - CFRelease(invocation); + CFRelease((__bridge CFTypeRef)(invocation)); if (objectToRelease) { - CFRelease(objectToRelease); + CFRelease((__bridge CFTypeRef)(objectToRelease)); } } -+ (void)updateProgressIndicator:(id *)indicator withProgress:(unsigned long long)progress ofTotal:(unsigned long long)total ++ (void)updateProgressIndicator:(id)indicator withProgress:(unsigned long long)progress ofTotal:(unsigned long long)total { #if TARGET_OS_IPHONE // Cocoa Touch: UIProgressView @@ -1914,7 +1899,7 @@ + (void)updateProgressIndicator:(id *)indicator withProgress:(unsigned long long SEL selector = @selector(setDoubleValue:); #endif - if (![*indicator respondsToSelector:selector]) { + if (![indicator respondsToSelector:selector]) { return; } @@ -1932,16 +1917,18 @@ - (void)requestStarted if ([self error] || [self mainRequest]) { return; } - if (delegate && [delegate respondsToSelector:didStartSelector]) { - [delegate performSelector:didStartSelector withObject:self]; + if ([self delegate] && [[self delegate] respondsToSelector:[self didStartSelector]]) { + ASISuppressPerformSelectorLeakWarning( + [[self delegate] performSelector:[self didStartSelector] withObject:self]; + ); } #if NS_BLOCKS_AVAILABLE if(startedBlock){ startedBlock(); } #endif - if (queue && [queue respondsToSelector:@selector(requestStarted:)]) { - [queue performSelector:@selector(requestStarted:) withObject:self]; + if (_queue && [_queue respondsToSelector:@selector(requestStarted:)]) { + [_queue performSelector:@selector(requestStarted:) withObject:self]; } } @@ -1971,8 +1958,10 @@ - (void)requestReceivedResponseHeaders:(NSMutableDictionary *)newResponseHeaders return; } - if (delegate && [delegate respondsToSelector:didReceiveResponseHeadersSelector]) { - [delegate performSelector:didReceiveResponseHeadersSelector withObject:self withObject:newResponseHeaders]; + if (_delegate && [_delegate respondsToSelector:_didReceiveResponseHeadersSelector]) { + ASISuppressPerformSelectorLeakWarning( + [_delegate performSelector:_didReceiveResponseHeadersSelector withObject:self withObject:newResponseHeaders]; + ); } #if NS_BLOCKS_AVAILABLE @@ -1981,8 +1970,8 @@ - (void)requestReceivedResponseHeaders:(NSMutableDictionary *)newResponseHeaders } #endif - if (queue && [queue respondsToSelector:@selector(request:didReceiveResponseHeaders:)]) { - [queue performSelector:@selector(request:didReceiveResponseHeaders:) withObject:self withObject:newResponseHeaders]; + if (_queue && [_queue respondsToSelector:@selector(request:didReceiveResponseHeaders:)]) { + [_queue performSelector:@selector(request:didReceiveResponseHeaders:) withObject:self withObject:newResponseHeaders]; } } @@ -1992,11 +1981,12 @@ - (void)requestWillRedirectToURL:(NSURL *)newURL if ([self error] || [self mainRequest]) { return; } - if (delegate && [delegate respondsToSelector:willRedirectSelector]) { - [delegate performSelector:willRedirectSelector withObject:self withObject:newURL]; + if (_delegate && [_delegate respondsToSelector:_willRedirectSelector]) { + ASISuppressPerformSelectorLeakWarning([_delegate performSelector:_willRedirectSelector withObject:self withObject:newURL]; + ); } - if (queue && [queue respondsToSelector:@selector(request:willRedirectToURL:)]) { - [queue performSelector:@selector(request:willRedirectToURL:) withObject:self withObject:newURL]; + if (_queue && [_queue respondsToSelector:@selector(request:willRedirectToURL:)]) { + [_queue performSelector:@selector(request:willRedirectToURL:) withObject:self withObject:newURL]; } } @@ -2020,8 +2010,10 @@ - (void)requestFinished /* ALWAYS CALLED ON MAIN THREAD! */ - (void)reportFinished { - if (delegate && [delegate respondsToSelector:didFinishSelector]) { - [delegate performSelector:didFinishSelector withObject:self]; + if (_delegate && [_delegate respondsToSelector:_didFinishSelector]) { + ASISuppressPerformSelectorLeakWarning( + [_delegate performSelector:_didFinishSelector withObject:self]; + ); } #if NS_BLOCKS_AVAILABLE @@ -2030,16 +2022,18 @@ - (void)reportFinished } #endif - if (queue && [queue respondsToSelector:@selector(requestFinished:)]) { - [queue performSelector:@selector(requestFinished:) withObject:self]; + if (_queue && [_queue respondsToSelector:@selector(requestFinished:)]) { + [_queue performSelector:@selector(requestFinished:) withObject:self]; } } /* ALWAYS CALLED ON MAIN THREAD! */ - (void)reportFailure { - if (delegate && [delegate respondsToSelector:didFailSelector]) { - [delegate performSelector:didFailSelector withObject:self]; + if (_delegate && [_delegate respondsToSelector:_didFailSelector]) { + ASISuppressPerformSelectorLeakWarning( + [_delegate performSelector:_didFailSelector withObject:self]; + ); } #if NS_BLOCKS_AVAILABLE @@ -2048,16 +2042,18 @@ - (void)reportFailure } #endif - if (queue && [queue respondsToSelector:@selector(requestFailed:)]) { - [queue performSelector:@selector(requestFailed:) withObject:self]; + if (_queue && [_queue respondsToSelector:@selector(requestFailed:)]) { + [_queue performSelector:@selector(requestFailed:) withObject:self]; } } /* ALWAYS CALLED ON MAIN THREAD! */ - (void)passOnReceivedData:(NSData *)data { - if (delegate && [delegate respondsToSelector:didReceiveDataSelector]) { - [delegate performSelector:didReceiveDataSelector withObject:self withObject:data]; + if (_delegate && [_delegate respondsToSelector:_didReceiveDataSelector]) { + ASISuppressPerformSelectorLeakWarning( + [_delegate performSelector:_didReceiveDataSelector withObject:self withObject:data]; + ); } #if NS_BLOCKS_AVAILABLE @@ -2135,7 +2131,7 @@ - (void)readResponseHeaders { [self setAuthenticationNeeded:ASINoAuthenticationNeededYet]; - CFHTTPMessageRef message = (CFHTTPMessageRef)CFReadStreamCopyProperty((CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPResponseHeader); + CFHTTPMessageRef message = (CFHTTPMessageRef)CFReadStreamCopyProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPResponseHeader); if (!message) { return; } @@ -2152,9 +2148,9 @@ - (void)readResponseHeaders } #endif - [self setResponseHeaders:[NSMakeCollectable(CFHTTPMessageCopyAllHeaderFields(message)) autorelease]]; + [self setResponseHeaders:(__bridge_transfer NSDictionary *)(CFHTTPMessageCopyAllHeaderFields(message))]; [self setResponseStatusCode:(int)CFHTTPMessageGetResponseStatusCode(message)]; - [self setResponseStatusMessage:[NSMakeCollectable(CFHTTPMessageCopyResponseStatusLine(message)) autorelease]]; + [self setResponseStatusMessage:(__bridge_transfer NSString *)(CFHTTPMessageCopyResponseStatusLine(message))]; if ([self downloadCache] && ([[self downloadCache] canUseCachedDataForRequest:self])) { @@ -2226,7 +2222,7 @@ - (void)readResponseHeaders // Do we need to redirect? if (![self willRedirect]) { // See if we got a Content-length header - NSString *cLength = [responseHeaders valueForKey:@"Content-Length"]; + NSString *cLength = [[self responseHeaders] valueForKey:@"Content-Length"]; ASIHTTPRequest *theRequest = self; if ([self mainRequest]) { theRequest = [self mainRequest]; @@ -2258,7 +2254,7 @@ - (void)readResponseHeaders NSString *connectionHeader = [[[self responseHeaders] objectForKey:@"Connection"] lowercaseString]; - NSString *httpVersion = [NSMakeCollectable(CFHTTPMessageCopyVersion(message)) autorelease]; + NSString *httpVersion = (__bridge_transfer NSString *)(CFHTTPMessageCopyVersion(message)); // Don't re-use the connection if the server is HTTP 1.0 and didn't send Connection: Keep-Alive if (![httpVersion isEqualToString:(NSString *)kCFHTTPVersion1_0] || [connectionHeader isEqualToString:@"keep-alive"]) { @@ -2298,13 +2294,13 @@ - (void)readResponseHeaders } CFRelease(message); - [self performSelectorOnMainThread:@selector(requestReceivedResponseHeaders:) withObject:[[[self responseHeaders] copy] autorelease] waitUntilDone:[NSThread isMainThread]]; + [self performSelectorOnMainThread:@selector(requestReceivedResponseHeaders:) withObject:[[self responseHeaders] copy] waitUntilDone:[NSThread isMainThread]]; } - (BOOL)willRedirect { // Do we need to redirect? - if (![self shouldRedirect] || ![responseHeaders valueForKey:@"Location"]) { + if (![self shouldRedirect] || ![[self responseHeaders] valueForKey:@"Location"]) { return NO; } @@ -2345,7 +2341,7 @@ - (BOOL)willRedirect } // Force the redirected request to rebuild the request headers (if not a 303, it will re-use old ones, and add any new ones) - [self setRedirectURL:[[NSURL URLWithString:[responseHeaders valueForKey:@"Location"] relativeToURL:[self url]] absoluteURL]]; + [self setRedirectURL:[[NSURL URLWithString:[[self responseHeaders] valueForKey:@"Location"] relativeToURL:[self url]] absoluteURL]]; [self setNeedsRedirect:YES]; // Clear the request cookies @@ -2400,15 +2396,15 @@ - (BOOL)applyProxyCredentials:(NSDictionary *)newCredentials if (newCredentials && proxyAuthentication && request) { // Apply whatever credentials we've built up to the old request - if (CFHTTPMessageApplyCredentialDictionary(request, proxyAuthentication, (CFMutableDictionaryRef)newCredentials, NULL)) { + if (CFHTTPMessageApplyCredentialDictionary(request, proxyAuthentication, (__bridge CFMutableDictionaryRef)newCredentials, NULL)) { //If we have credentials and they're ok, let's save them to the keychain if (useKeychainPersistence) { [self saveProxyCredentialsToKeychain:newCredentials]; } - if (useSessionPersistence) { + if ([self useSessionPersistence]) { NSMutableDictionary *sessionProxyCredentials = [NSMutableDictionary dictionary]; - [sessionProxyCredentials setObject:(id)proxyAuthentication forKey:@"Authentication"]; + [sessionProxyCredentials setObject:(__bridge id)proxyAuthentication forKey:@"Authentication"]; [sessionProxyCredentials setObject:newCredentials forKey:@"Credentials"]; [sessionProxyCredentials setObject:[self proxyHost] forKey:@"Host"]; [sessionProxyCredentials setObject:[NSNumber numberWithInt:[self proxyPort]] forKey:@"Port"]; @@ -2430,16 +2426,16 @@ - (BOOL)applyCredentials:(NSDictionary *)newCredentials if (newCredentials && requestAuthentication && request) { // Apply whatever credentials we've built up to the old request - if (CFHTTPMessageApplyCredentialDictionary(request, requestAuthentication, (CFMutableDictionaryRef)newCredentials, NULL)) { + if (CFHTTPMessageApplyCredentialDictionary(request, requestAuthentication, (__bridge CFMutableDictionaryRef)newCredentials, NULL)) { //If we have credentials and they're ok, let's save them to the keychain if (useKeychainPersistence) { [self saveCredentialsToKeychain:newCredentials]; } - if (useSessionPersistence) { + if ([self useSessionPersistence]) { NSMutableDictionary *sessionCredentials = [NSMutableDictionary dictionary]; - [sessionCredentials setObject:(id)requestAuthentication forKey:@"Authentication"]; + [sessionCredentials setObject:(__bridge id)requestAuthentication forKey:@"Authentication"]; [sessionCredentials setObject:newCredentials forKey:@"Credentials"]; [sessionCredentials setObject:[self url] forKey:@"URL"]; [sessionCredentials setObject:[self authenticationScheme] forKey:@"AuthenticationScheme"]; @@ -2460,7 +2456,7 @@ - (BOOL)applyCredentials:(NSDictionary *)newCredentials - (NSMutableDictionary *)findProxyCredentials { - NSMutableDictionary *newCredentials = [[[NSMutableDictionary alloc] init] autorelease]; + NSMutableDictionary *newCredentials = [[NSMutableDictionary alloc] init]; NSString *user = nil; NSString *pass = nil; @@ -2534,7 +2530,7 @@ - (NSMutableDictionary *)findProxyCredentials - (NSMutableDictionary *)findCredentials { - NSMutableDictionary *newCredentials = [[[NSMutableDictionary alloc] init] autorelease]; + NSMutableDictionary *newCredentials = [[NSMutableDictionary alloc] init]; // First, let's look at the url to see if the username and password were included NSString *user = [[self url] user]; @@ -2766,10 +2762,10 @@ - (void)attemptToApplyProxyCredentialsAndResume // Read authentication data if (!proxyAuthentication) { - CFHTTPMessageRef responseHeader = (CFHTTPMessageRef) CFReadStreamCopyProperty((CFReadStreamRef)[self readStream],kCFStreamPropertyHTTPResponseHeader); + CFHTTPMessageRef responseHeader = (CFHTTPMessageRef) CFReadStreamCopyProperty((__bridge CFReadStreamRef)[self readStream],kCFStreamPropertyHTTPResponseHeader); proxyAuthentication = CFHTTPAuthenticationCreateFromResponse(NULL, responseHeader); CFRelease(responseHeader); - [self setProxyAuthenticationScheme:[NSMakeCollectable(CFHTTPAuthenticationCopyMethod(proxyAuthentication)) autorelease]]; + [self setProxyAuthenticationScheme:(__bridge_transfer NSString *)(CFHTTPAuthenticationCopyMethod(proxyAuthentication))]; } // If we haven't got a CFHTTPAuthenticationRef by now, something is badly wrong, so we'll have to give up @@ -2782,7 +2778,7 @@ - (void)attemptToApplyProxyCredentialsAndResume // Get the authentication realm [self setProxyAuthenticationRealm:nil]; if (!CFHTTPAuthenticationRequiresAccountDomain(proxyAuthentication)) { - [self setProxyAuthenticationRealm:[NSMakeCollectable(CFHTTPAuthenticationCopyRealm(proxyAuthentication)) autorelease]]; + [self setProxyAuthenticationRealm:(__bridge_transfer NSString *)(CFHTTPAuthenticationCopyRealm(proxyAuthentication))]; } // See if authentication is valid @@ -2799,7 +2795,7 @@ - (void)attemptToApplyProxyCredentialsAndResume [delegateAuthenticationLock lock]; // We know the credentials we just presented are bad, we should remove them from the session store too - [[self class] removeProxyAuthenticationCredentialsFromSessionStore:proxyCredentials]; + [[self class] removeProxyAuthenticationCredentialsFromSessionStore:_proxyCredentials]; [self setProxyCredentials:nil]; @@ -2841,10 +2837,10 @@ - (void)attemptToApplyProxyCredentialsAndResume [self cancelLoad]; - if (proxyCredentials) { + if (_proxyCredentials) { // We use startRequest rather than starting all over again in load request because NTLM requires we reuse the request - if ((([self proxyAuthenticationScheme] != (NSString *)kCFHTTPAuthenticationSchemeNTLM) || [self proxyAuthenticationRetryCount] < 2) && [self applyProxyCredentials:proxyCredentials]) { + if ((([self proxyAuthenticationScheme] != (NSString *)kCFHTTPAuthenticationSchemeNTLM) || [self proxyAuthenticationRetryCount] < 2) && [self applyProxyCredentials:_proxyCredentials]) { [self startRequest]; // We've failed NTLM authentication twice, we should assume our credentials are wrong @@ -2943,10 +2939,10 @@ - (void)attemptToApplyCredentialsAndResume // Read authentication data if (!requestAuthentication) { - CFHTTPMessageRef responseHeader = (CFHTTPMessageRef) CFReadStreamCopyProperty((CFReadStreamRef)[self readStream],kCFStreamPropertyHTTPResponseHeader); + CFHTTPMessageRef responseHeader = (CFHTTPMessageRef) CFReadStreamCopyProperty((__bridge CFReadStreamRef)[self readStream],kCFStreamPropertyHTTPResponseHeader); requestAuthentication = CFHTTPAuthenticationCreateFromResponse(NULL, responseHeader); CFRelease(responseHeader); - [self setAuthenticationScheme:[NSMakeCollectable(CFHTTPAuthenticationCopyMethod(requestAuthentication)) autorelease]]; + [self setAuthenticationScheme:(__bridge_transfer NSString *)(CFHTTPAuthenticationCopyMethod(requestAuthentication))]; } if (!requestAuthentication) { @@ -2962,7 +2958,7 @@ - (void)attemptToApplyCredentialsAndResume // Get the authentication realm [self setAuthenticationRealm:nil]; if (!CFHTTPAuthenticationRequiresAccountDomain(requestAuthentication)) { - [self setAuthenticationRealm:[NSMakeCollectable(CFHTTPAuthenticationCopyRealm(requestAuthentication)) autorelease]]; + [self setAuthenticationRealm:(__bridge_transfer NSString *)(CFHTTPAuthenticationCopyRealm(requestAuthentication))]; } #if DEBUG_HTTP_AUTHENTICATION @@ -2997,7 +2993,7 @@ - (void)attemptToApplyCredentialsAndResume [delegateAuthenticationLock lock]; // We know the credentials we just presented are bad, we should remove them from the session store too - [[self class] removeAuthenticationCredentialsFromSessionStore:requestCredentials]; + [[self class] removeAuthenticationCredentialsFromSessionStore:_requestCredentials]; [self setRequestCredentials:nil]; // If the user cancelled authentication via a dialog presented by another request, our queue may have cancelled us @@ -3060,9 +3056,9 @@ - (void)attemptToApplyCredentialsAndResume [self cancelLoad]; - if (requestCredentials) { + if (_requestCredentials) { - if ((([self authenticationScheme] != (NSString *)kCFHTTPAuthenticationSchemeNTLM) || [self authenticationRetryCount] < 2) && [self applyCredentials:requestCredentials]) { + if ((([self authenticationScheme] != (NSString *)kCFHTTPAuthenticationSchemeNTLM) || [self authenticationRetryCount] < 2) && [self applyCredentials:_requestCredentials]) { [self startRequest]; // We've failed NTLM authentication twice, we should assume our credentials are wrong @@ -3173,17 +3169,15 @@ - (void)addBasicAuthenticationHeaderWithUsername:(NSString *)theUsername andPass - (void)handleNetworkEvent:(CFStreamEventType)type { - NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; - + @autoreleasepool { [[self cancelledLock] lock]; if ([self complete] || [self isCancelled]) { [[self cancelledLock] unlock]; - [pool drain]; return; } - CFRetain(self); + CFRetain((__bridge CFTypeRef)(self)); // Dispatch the stream events. switch (type) { @@ -3215,8 +3209,8 @@ - (void)handleNetworkEvent:(CFStreamEventType)type [self attemptToApplyCredentialsAndResume]; } - CFRelease(self); - [pool drain]; + CFRelease((__bridge CFTypeRef)(self)); + } } - (BOOL)willAskDelegateToConfirmRedirect @@ -3232,7 +3226,7 @@ - (BOOL)willAskDelegateToConfirmRedirect // Either the delegate or the queue's delegate is interested in being told when we are about to redirect if (needToAskDelegateAboutRedirect) { - NSURL *newURL = [[[self redirectURL] copy] autorelease]; + NSURL *newURL = [[self redirectURL] copy]; [self setRedirectURL:nil]; [self performSelectorOnMainThread:@selector(requestWillRedirectToURL:) withObject:newURL waitUntilDone:[NSThread isMainThread]]; return true; @@ -3254,14 +3248,14 @@ - (void)handleBytesAvailable // In certain (presumably very rare) circumstances, handleBytesAvailable seems to be called when there isn't actually any data available // We'll check that there is actually data available to prevent blocking on CFReadStreamRead() // So far, I've only seen this in the stress tests, so it might never happen in real-world situations. - if (!CFReadStreamHasBytesAvailable((CFReadStreamRef)[self readStream])) { + if (!CFReadStreamHasBytesAvailable((__bridge CFReadStreamRef)[self readStream])) { return; } long long bufferSize = 16384; - if (contentLength > 262144) { + if (_contentLength > 262144) { bufferSize = 262144; - } else if (contentLength > 65536) { + } else if (_contentLength > 65536) { bufferSize = 65536; } @@ -3357,7 +3351,7 @@ - (void)handleBytesAvailable } } - [self setFileDownloadOutputStream:[[[NSOutputStream alloc] initToFileAtPath:[self temporaryFileDownloadPath] append:append] autorelease]]; + [self setFileDownloadOutputStream:[[NSOutputStream alloc] initToFileAtPath:[self temporaryFileDownloadPath] append:append]]; [[self fileDownloadOutputStream] open]; } @@ -3370,7 +3364,7 @@ - (void)handleBytesAvailable [self setTemporaryUncompressedDataDownloadPath:[NSTemporaryDirectory() stringByAppendingPathComponent:[[NSProcessInfo processInfo] globallyUniqueString]]]; } - [self setInflatedFileDownloadOutputStream:[[[NSOutputStream alloc] initToFileAtPath:[self temporaryUncompressedDataDownloadPath] append:append] autorelease]]; + [self setInflatedFileDownloadOutputStream:[[NSOutputStream alloc] initToFileAtPath:[self temporaryUncompressedDataDownloadPath] append:append]]; [[self inflatedFileDownloadOutputStream] open]; } @@ -3381,9 +3375,9 @@ - (void)handleBytesAvailable //Otherwise, let's add the data to our in-memory store } else { if ([self isResponseCompressed] && ![self shouldWaitToInflateCompressedResponses]) { - [rawResponseData appendData:inflatedData]; + [_rawResponseData appendData:inflatedData]; } else { - [rawResponseData appendBytes:buffer length:bytesRead]; + [_rawResponseData appendBytes:buffer length:bytesRead]; } } } @@ -3404,8 +3398,8 @@ - (void)handleStreamComplete [progressLock lock]; // Find out how much data we've uploaded so far - [self setLastBytesSent:totalBytesSent]; - [self setTotalBytesSent:[[NSMakeCollectable(CFReadStreamCopyProperty((CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPRequestBytesWrittenCount)) autorelease] unsignedLongLongValue]]; + [self setLastBytesSent:_totalBytesSent]; + [self setTotalBytesSent:[(__bridge_transfer id)(CFReadStreamCopyProperty((__bridge CFReadStreamRef)[self readStream], kCFStreamPropertyHTTPRequestBytesWrittenCount)) unsignedLongLongValue]]; [self setComplete:YES]; if (![self contentLength]) { [self setContentLength:[self totalBytesRead]]; @@ -3447,7 +3441,7 @@ - (void)handleStreamComplete // Response should already have been inflated, move the temporary file to the destination path } else { NSError *moveError = nil; - [[[[NSFileManager alloc] init] autorelease] moveItemAtPath:[self temporaryUncompressedDataDownloadPath] toPath:[self downloadDestinationPath] error:&moveError]; + [[[NSFileManager alloc] init] moveItemAtPath:[self temporaryUncompressedDataDownloadPath] toPath:[self downloadDestinationPath] error:&moveError]; if (moveError) { fileError = [NSError errorWithDomain:NetworkRequestErrorDomain code:ASIFileManagementError userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"Failed to move file from '%@' to '%@'",[self temporaryFileDownloadPath],[self downloadDestinationPath]],NSLocalizedDescriptionKey,moveError,NSUnderlyingErrorKey,nil]]; } @@ -3467,7 +3461,7 @@ - (void)handleStreamComplete //Move the temporary file to the destination path if (!fileError) { - [[[[NSFileManager alloc] init] autorelease] moveItemAtPath:[self temporaryFileDownloadPath] toPath:[self downloadDestinationPath] error:&moveError]; + [[[NSFileManager alloc] init] moveItemAtPath:[self temporaryFileDownloadPath] toPath:[self downloadDestinationPath] error:&moveError]; if (moveError) { fileError = [NSError errorWithDomain:NetworkRequestErrorDomain code:ASIFileManagementError userInfo:[NSDictionary dictionaryWithObjectsAndKeys:[NSString stringWithFormat:@"Failed to move file from '%@' to '%@'",[self temporaryFileDownloadPath],[self downloadDestinationPath]],NSLocalizedDescriptionKey,moveError,NSUnderlyingErrorKey,nil]]; } @@ -3523,7 +3517,7 @@ - (void)handleStreamComplete - (void)markAsFinished { // Autoreleased requests may well be dealloced here otherwise - CFRetain(self); + CFRetain((__bridge CFTypeRef)(self)); // dealloc won't be called when running with GC, so we'll clean these up now if (request) { @@ -3557,7 +3551,11 @@ - (void)markAsFinished #if TARGET_OS_IPHONE && __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_4_0 if ([ASIHTTPRequest isMultitaskingSupported] && [self shouldContinueWhenAppEntersBackground]) { - dispatch_async(dispatch_get_main_queue(), ^{ + // This delay causes some overlapping between distinct requests. Thus, we avoid that our + // app is stopped until everything is ok.. + double delayInSeconds = 0.5; + dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, delayInSeconds * NSEC_PER_SEC); + dispatch_after(popTime, dispatch_get_main_queue(), ^(void){ if (backgroundTask != UIBackgroundTaskInvalid) { [[UIApplication sharedApplication] endBackgroundTask:backgroundTask]; backgroundTask = UIBackgroundTaskInvalid; @@ -3565,7 +3563,7 @@ - (void)markAsFinished }); } #endif - CFRelease(self); + CFRelease((__bridge CFTypeRef)(self)); } - (void)useDataFromCache @@ -3650,7 +3648,7 @@ - (BOOL)retryUsingNewConnection - (void)handleStreamError { - NSError *underlyingError = [NSMakeCollectable(CFReadStreamCopyError((CFReadStreamRef)[self readStream])) autorelease]; + NSError *underlyingError = (__bridge_transfer NSError *)(CFReadStreamCopyError((__bridge CFReadStreamRef)[self readStream])); if (![self error]) { // We may already have handled this error @@ -3711,8 +3709,8 @@ - (void)scheduleReadStream // Reset the timeout [self setLastActivityTime:[NSDate date]]; - CFStreamClientContext ctxt = {0, self, NULL, NULL, NULL}; - CFReadStreamSetClient((CFReadStreamRef)[self readStream], kNetworkEvents, ReadStreamClientCallBack, &ctxt); + CFStreamClientContext ctxt = {0, (__bridge void *)(self), NULL, NULL, NULL}; + CFReadStreamSetClient((__bridge CFReadStreamRef)[self readStream], kNetworkEvents, ReadStreamClientCallBack, &ctxt); [[self readStream] scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:[self runLoopMode]]; [self setReadStreamIsScheduled:YES]; } @@ -3734,7 +3732,7 @@ - (void)unscheduleReadStream } [connectionsLock unlock]; - CFReadStreamSetClient((CFReadStreamRef)[self readStream], kCFStreamEventNone, NULL, NULL); + CFReadStreamSetClient((__bridge CFReadStreamRef)[self readStream], kCFStreamEventNone, NULL, NULL); [[self readStream] removeFromRunLoop:[NSRunLoop currentRunLoop] forMode:[self runLoopMode]]; [self setReadStreamIsScheduled:NO]; } @@ -3792,7 +3790,7 @@ - (BOOL)removeTemporaryCompressedUploadFile + (BOOL)removeFileAtPath:(NSString *)path error:(NSError **)err { - NSFileManager *fileManager = [[[NSFileManager alloc] init] autorelease]; + NSFileManager *fileManager = [[NSFileManager alloc] init]; if ([fileManager fileExistsAtPath:path]) { NSError *removeError = nil; @@ -3828,12 +3826,12 @@ - (BOOL)configureProxies } else { #if TARGET_OS_IPHONE - NSDictionary *proxySettings = [NSMakeCollectable(CFNetworkCopySystemProxySettings()) autorelease]; + NSDictionary *proxySettings = (__bridge_transfer NSDictionary *)(CFNetworkCopySystemProxySettings()); #else NSDictionary *proxySettings = [NSMakeCollectable(SCDynamicStoreCopyProxies(NULL)) autorelease]; #endif - proxies = [NSMakeCollectable(CFNetworkCopyProxiesForURL((CFURLRef)[self url], (CFDictionaryRef)proxySettings)) autorelease]; + proxies = (__bridge_transfer NSArray *)(CFNetworkCopyProxiesForURL((__bridge CFURLRef)[self url], (__bridge CFDictionaryRef)proxySettings)); // Now check to see if the proxy settings contained a PAC url, we need to run the script to get the real list of proxies if so NSDictionary *settings = [proxies objectAtIndex:0]; @@ -3869,7 +3867,7 @@ - (void)fetchPACFile { // For file:// urls, we'll use an async NSInputStream (ASIHTTPRequest does not support file:// urls) if ([[self PACurl] isFileURL]) { - NSInputStream *stream = [[[NSInputStream alloc] initWithFileAtPath:[[self PACurl] path]] autorelease]; + NSInputStream *stream = [[NSInputStream alloc] initWithFileAtPath:[[self PACurl] path]]; [self setPACFileReadStream:stream]; [stream setDelegate:(id)self]; [stream scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:[self runLoopMode]]; @@ -3955,7 +3953,7 @@ - (void)stream:(NSStream *)stream handleEvent:(NSStreamEvent)eventCode static NSStringEncoding encodingsToTry[2] = {NSUTF8StringEncoding,NSISOLatin1StringEncoding}; NSUInteger i; for (i=0; i<2; i++) { - NSString *pacScript = [[[NSString alloc] initWithBytes:[[self PACFileData] bytes] length:[[self PACFileData] length] encoding:encodingsToTry[i]] autorelease]; + NSString *pacScript = [[NSString alloc] initWithBytes:[[self PACFileData] bytes] length:[[self PACFileData] length] encoding:encodingsToTry[i]]; if (pacScript) { [self runPACScript:pacScript]; break; @@ -3981,11 +3979,11 @@ - (void)runPACScript:(NSString *)script // Work around . This dummy call to // CFNetworkCopyProxiesForURL initialise some state within CFNetwork // that is required by CFNetworkCopyProxiesForAutoConfigurationScript. - CFRelease(CFNetworkCopyProxiesForURL((CFURLRef)[self url], NULL)); + CFRelease(CFNetworkCopyProxiesForURL((__bridge CFURLRef)[self url], NULL)); // Obtain the list of proxies by running the autoconfiguration script CFErrorRef err = NULL; - NSArray *proxies = [NSMakeCollectable(CFNetworkCopyProxiesForAutoConfigurationScript((CFStringRef)script,(CFURLRef)[self url], &err)) autorelease]; + NSArray *proxies = (__bridge_transfer NSArray *)(CFNetworkCopyProxiesForAutoConfigurationScript((__bridge CFStringRef)script,(__bridge CFURLRef)[self url], &err)); if (!err && [proxies count] > 0) { NSDictionary *settings = [proxies objectAtIndex:0]; [self setProxyHost:[settings objectForKey:(NSString *)kCFProxyHostNameKey]]; @@ -4053,8 +4051,8 @@ - (id)copyWithZone:(NSZone *)zone [newRequest setPostBody:[self postBody]]; [newRequest setShouldStreamPostDataFromDisk:[self shouldStreamPostDataFromDisk]]; [newRequest setPostBodyFilePath:[self postBodyFilePath]]; - [newRequest setRequestHeaders:[[[self requestHeaders] mutableCopyWithZone:zone] autorelease]]; - [newRequest setRequestCookies:[[[self requestCookies] mutableCopyWithZone:zone] autorelease]]; + [newRequest setRequestHeaders:[[self requestHeaders] mutableCopyWithZone:zone]]; + [newRequest setRequestCookies:[[self requestCookies] mutableCopyWithZone:zone]]; [newRequest setUseCookiePersistence:[self useCookiePersistence]]; [newRequest setUseKeychainPersistence:[self useKeychainPersistence]]; [newRequest setUseSessionPersistence:[self useSessionPersistence]]; @@ -4085,13 +4083,13 @@ - (id)copyWithZone:(NSZone *)zone [newRequest setShowAccurateProgress:[self showAccurateProgress]]; [newRequest setDefaultResponseEncoding:[self defaultResponseEncoding]]; [newRequest setAllowResumeForFileDownloads:[self allowResumeForFileDownloads]]; - [newRequest setUserInfo:[[[self userInfo] copyWithZone:zone] autorelease]]; + [newRequest setUserInfo:[[self userInfo] copyWithZone:zone]]; [newRequest setTag:[self tag]]; [newRequest setUseHTTPVersionOne:[self useHTTPVersionOne]]; [newRequest setShouldRedirect:[self shouldRedirect]]; [newRequest setValidatesSecureCertificate:[self validatesSecureCertificate]]; [newRequest setClientCertificateIdentity:clientCertificateIdentity]; - [newRequest setClientCertificates:[[clientCertificates copy] autorelease]]; + [newRequest setClientCertificates:[_clientCertificates copy]]; [newRequest setPACurl:[self PACurl]]; [newRequest setShouldPresentCredentialsBeforeChallenge:[self shouldPresentCredentialsBeforeChallenge]]; [newRequest setNumberOfTimesToRetryOnTimeout:[self numberOfTimesToRetryOnTimeout]]; @@ -4278,31 +4276,31 @@ - (NSDictionary *)findSessionAuthenticationCredentials + (void)saveCredentials:(NSURLCredential *)credentials forHost:(NSString *)host port:(int)port protocol:(NSString *)protocol realm:(NSString *)realm { - NSURLProtectionSpace *protectionSpace = [[[NSURLProtectionSpace alloc] initWithHost:host port:port protocol:protocol realm:realm authenticationMethod:NSURLAuthenticationMethodDefault] autorelease]; + NSURLProtectionSpace *protectionSpace = [[NSURLProtectionSpace alloc] initWithHost:host port:port protocol:protocol realm:realm authenticationMethod:NSURLAuthenticationMethodDefault]; [[NSURLCredentialStorage sharedCredentialStorage] setDefaultCredential:credentials forProtectionSpace:protectionSpace]; } + (void)saveCredentials:(NSURLCredential *)credentials forProxy:(NSString *)host port:(int)port realm:(NSString *)realm { - NSURLProtectionSpace *protectionSpace = [[[NSURLProtectionSpace alloc] initWithProxyHost:host port:port type:NSURLProtectionSpaceHTTPProxy realm:realm authenticationMethod:NSURLAuthenticationMethodDefault] autorelease]; + NSURLProtectionSpace *protectionSpace = [[NSURLProtectionSpace alloc] initWithProxyHost:host port:port type:NSURLProtectionSpaceHTTPProxy realm:realm authenticationMethod:NSURLAuthenticationMethodDefault]; [[NSURLCredentialStorage sharedCredentialStorage] setDefaultCredential:credentials forProtectionSpace:protectionSpace]; } + (NSURLCredential *)savedCredentialsForHost:(NSString *)host port:(int)port protocol:(NSString *)protocol realm:(NSString *)realm { - NSURLProtectionSpace *protectionSpace = [[[NSURLProtectionSpace alloc] initWithHost:host port:port protocol:protocol realm:realm authenticationMethod:NSURLAuthenticationMethodDefault] autorelease]; + NSURLProtectionSpace *protectionSpace = [[NSURLProtectionSpace alloc] initWithHost:host port:port protocol:protocol realm:realm authenticationMethod:NSURLAuthenticationMethodDefault]; return [[NSURLCredentialStorage sharedCredentialStorage] defaultCredentialForProtectionSpace:protectionSpace]; } + (NSURLCredential *)savedCredentialsForProxy:(NSString *)host port:(int)port protocol:(NSString *)protocol realm:(NSString *)realm { - NSURLProtectionSpace *protectionSpace = [[[NSURLProtectionSpace alloc] initWithProxyHost:host port:port type:NSURLProtectionSpaceHTTPProxy realm:realm authenticationMethod:NSURLAuthenticationMethodDefault] autorelease]; + NSURLProtectionSpace *protectionSpace = [[NSURLProtectionSpace alloc] initWithProxyHost:host port:port type:NSURLProtectionSpaceHTTPProxy realm:realm authenticationMethod:NSURLAuthenticationMethodDefault]; return [[NSURLCredentialStorage sharedCredentialStorage] defaultCredentialForProtectionSpace:protectionSpace]; } + (void)removeCredentialsForHost:(NSString *)host port:(int)port protocol:(NSString *)protocol realm:(NSString *)realm { - NSURLProtectionSpace *protectionSpace = [[[NSURLProtectionSpace alloc] initWithHost:host port:port protocol:protocol realm:realm authenticationMethod:NSURLAuthenticationMethodDefault] autorelease]; + NSURLProtectionSpace *protectionSpace = [[NSURLProtectionSpace alloc] initWithHost:host port:port protocol:protocol realm:realm authenticationMethod:NSURLAuthenticationMethodDefault]; NSURLCredential *credential = [[NSURLCredentialStorage sharedCredentialStorage] defaultCredentialForProtectionSpace:protectionSpace]; if (credential) { [[NSURLCredentialStorage sharedCredentialStorage] removeCredential:credential forProtectionSpace:protectionSpace]; @@ -4311,7 +4309,7 @@ + (void)removeCredentialsForHost:(NSString *)host port:(int)port protocol:(NSStr + (void)removeCredentialsForProxy:(NSString *)host port:(int)port realm:(NSString *)realm { - NSURLProtectionSpace *protectionSpace = [[[NSURLProtectionSpace alloc] initWithProxyHost:host port:port type:NSURLProtectionSpaceHTTPProxy realm:realm authenticationMethod:NSURLAuthenticationMethodDefault] autorelease]; + NSURLProtectionSpace *protectionSpace = [[NSURLProtectionSpace alloc] initWithProxyHost:host port:port type:NSURLProtectionSpaceHTTPProxy realm:realm authenticationMethod:NSURLAuthenticationMethodDefault]; NSURLCredential *credential = [[NSURLCredentialStorage sharedCredentialStorage] defaultCredentialForProtectionSpace:protectionSpace]; if (credential) { [[NSURLCredentialStorage sharedCredentialStorage] removeCredential:credential forProtectionSpace:protectionSpace]; @@ -4324,9 +4322,8 @@ + (NSMutableArray *)sessionCookies if (!sessionCookies) { [ASIHTTPRequest setSessionCookies:[NSMutableArray array]]; } - NSMutableArray *cookies = [[sessionCookies retain] autorelease]; [sessionCookiesLock unlock]; - return cookies; + return sessionCookies; } + (void)setSessionCookies:(NSMutableArray *)newSessionCookies @@ -4336,8 +4333,7 @@ + (void)setSessionCookies:(NSMutableArray *)newSessionCookies for (NSHTTPCookie *cookie in sessionCookies) { [[NSHTTPCookieStorage sharedHTTPCookieStorage] deleteCookie:cookie]; } - [sessionCookies release]; - sessionCookies = [newSessionCookies retain]; + sessionCookies = newSessionCookies; [sessionCookiesLock unlock]; } @@ -4385,7 +4381,7 @@ + (NSString *)defaultUserAgentString } NSData *latin1Data = [appName dataUsingEncoding:NSUTF8StringEncoding]; - appName = [[[NSString alloc] initWithData:latin1Data encoding:NSISOLatin1StringEncoding] autorelease]; + appName = [[NSString alloc] initWithData:latin1Data encoding:NSISOLatin1StringEncoding]; // If we couldn't find one, we'll give up (and ASIHTTPRequest will use the standard CFNetwork user agent) if (!appName) { @@ -4436,7 +4432,7 @@ + (NSString *)defaultUserAgentString // Takes the form "My Application 1.0 (Macintosh; Mac OS X 10.5.7; en_GB)" [self setDefaultUserAgentString:[NSString stringWithFormat:@"%@ %@ (%@; %@ %@; %@)", appName, appVersion, deviceName, OSName, OSVersion, locale]]; } - return [[defaultUserAgent retain] autorelease]; + return defaultUserAgent; } return nil; } @@ -4447,7 +4443,6 @@ + (void)setDefaultUserAgentString:(NSString *)agent if (defaultUserAgent == agent) { return; } - [defaultUserAgent release]; defaultUserAgent = [agent copy]; } } @@ -4457,17 +4452,17 @@ + (void)setDefaultUserAgentString:(NSString *)agent + (NSString *)mimeTypeForFileAtPath:(NSString *)path { - if (![[[[NSFileManager alloc] init] autorelease] fileExistsAtPath:path]) { + if (![[[NSFileManager alloc] init] fileExistsAtPath:path]) { return nil; } // Borrowed from http://stackoverflow.com/questions/2439020/wheres-the-iphone-mime-type-database - CFStringRef UTI = UTTypeCreatePreferredIdentifierForTag(kUTTagClassFilenameExtension, (CFStringRef)[path pathExtension], NULL); + CFStringRef UTI = UTTypeCreatePreferredIdentifierForTag(kUTTagClassFilenameExtension, (__bridge CFStringRef)[path pathExtension], NULL); CFStringRef MIMEType = UTTypeCopyPreferredTagWithClass (UTI, kUTTagClassMIMEType); CFRelease(UTI); if (!MIMEType) { return @"application/octet-stream"; } - return [NSMakeCollectable(MIMEType) autorelease]; + return (__bridge_transfer NSString *)(MIMEType); } #pragma mark bandwidth measurement / throttling @@ -4559,8 +4554,7 @@ + (void)recordBandwidthUsage ASI_DEBUG_LOG(@"[THROTTLING] ===Used: %u bytes of bandwidth in last measurement period===",bandwidthUsedInLastSecond); #endif [bandwidthUsageTracker addObject:[NSNumber numberWithUnsignedLong:bandwidthUsedInLastSecond]]; - [bandwidthMeasurementDate release]; - bandwidthMeasurementDate = [[NSDate dateWithTimeIntervalSinceNow:1] retain]; + bandwidthMeasurementDate = [NSDate dateWithTimeIntervalSinceNow:1]; bandwidthUsedInLastSecond = 0; NSUInteger measurements = [bandwidthUsageTracker count]; @@ -4569,7 +4563,7 @@ + (void)recordBandwidthUsage totalBytes += [bytes unsignedLongValue]; } if (measurements > 0) - averageBandwidthUsedPerSecond = totalBytes/measurements; + averageBandwidthUsedPerSecond = totalBytes/measurements; } + (unsigned long)averageBandwidthUsedPerSecond @@ -4605,7 +4599,6 @@ + (void)measureBandwidthUsage // Yes, put this request to sleep until a second is up, with extra added punishment sleeping time for being very naughty (we have used more bandwidth than we were allowed) double extraSleepyTime = (-bytesRemaining/(maxBandwidthPerSecond*1.0)); - [throttleWakeUpTime release]; throttleWakeUpTime = [[NSDate alloc] initWithTimeInterval:extraSleepyTime sinceDate:bandwidthMeasurementDate]; } } @@ -4626,8 +4619,7 @@ + (unsigned long)maxUploadReadLength } if (toRead == 0 || !bandwidthMeasurementDate || [bandwidthMeasurementDate timeIntervalSinceNow] < -0) { - [throttleWakeUpTime release]; - throttleWakeUpTime = [bandwidthMeasurementDate retain]; + throttleWakeUpTime = bandwidthMeasurementDate; } [bandwidthThrottlingLock unlock]; return (unsigned long)toRead; @@ -4663,7 +4655,7 @@ + (void)throttleBandwidthForWWANUsingLimit:(unsigned long)limit + (void)registerForNetworkReachabilityNotifications { - [[Reachability reachabilityForInternetConnection] startNotifier]; + [[_Reachability reachabilityForInternetConnection] startNotifier]; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(reachabilityChanged:) name:kReachabilityChangedNotification object:nil]; } @@ -4675,7 +4667,7 @@ + (void)unsubscribeFromNetworkReachabilityNotifications + (BOOL)isNetworkReachableViaWWAN { - return ([[Reachability reachabilityForInternetConnection] currentReachabilityStatus] == ReachableViaWWAN); + return ([[_Reachability reachabilityForInternetConnection] currentReachabilityStatus] == ReachableViaWWAN); } + (void)reachabilityChanged:(NSNotification *)note @@ -4691,7 +4683,7 @@ + (void)reachabilityChanged:(NSNotification *)note // Returns the shared queue + (NSOperationQueue *)sharedQueue { - return [[sharedQueue retain] autorelease]; + return sharedQueue; } #pragma mark cache @@ -4699,8 +4691,6 @@ + (NSOperationQueue *)sharedQueue + (void)setDefaultCache:(id )cache { @synchronized (self) { - [cache retain]; - [defaultCache release]; defaultCache = cache; } } @@ -4708,7 +4698,7 @@ + (void)setDefaultCache:(id )cache + (id )defaultCache { @synchronized(self) { - return [[defaultCache retain] autorelease]; + return defaultCache; } return nil; } @@ -4793,9 +4783,9 @@ + (void)runRequests BOOL runAlways = YES; // Introduced to cheat Static Analyzer while (runAlways) { - NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; + @autoreleasepool { CFRunLoopRunInMode(kCFRunLoopDefaultMode, 1.0e10, true); - [pool drain]; + } } // Should never be called, but anyway @@ -4845,7 +4835,7 @@ + (NSString*)base64forData:(NSData*)theData { output[theIndex + 3] = (i + 2) < length ? table[(value >> 0) & 0x3F] : '='; } - return [[[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding] autorelease]; + return [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding]; } + (NSDate *)expiryDateForRequest:(ASIHTTPRequest *)request maxAge:(NSTimeInterval)maxAge @@ -4880,8 +4870,8 @@ + (NSDate *)expiryDateForRequest:(ASIHTTPRequest *)request maxAge:(NSTimeInterva // Based on hints from http://stackoverflow.com/questions/1850824/parsing-a-rfc-822-date-with-nsdateformatter + (NSDate *)dateFromRFC1123String:(NSString *)string { - NSDateFormatter *formatter = [[[NSDateFormatter alloc] init] autorelease]; - [formatter setLocale:[[[NSLocale alloc] initWithLocaleIdentifier:@"en_US_POSIX"] autorelease]]; + NSDateFormatter *formatter = [[NSDateFormatter alloc] init]; + [formatter setLocale:[[NSLocale alloc] initWithLocaleIdentifier:@"en_US_POSIX"]]; // Does the string include a week day? NSString *day = @""; if ([string rangeOfString:@","].location != NSNotFound) { @@ -4916,7 +4906,7 @@ + (void)parseMimeType:(NSString **)mimeType andResponseEncoding:(NSStringEncodin } if (IANAEncoding) { - CFStringEncoding cfEncoding = CFStringConvertIANACharSetNameToEncoding((CFStringRef)IANAEncoding); + CFStringEncoding cfEncoding = CFStringConvertIANACharSetNameToEncoding((__bridge CFStringRef)IANAEncoding); if (cfEncoding != kCFStringEncodingInvalidId) { *stringEncoding = CFStringConvertEncodingToNSStringEncoding(cfEncoding); } @@ -4928,196 +4918,100 @@ + (void)parseMimeType:(NSString **)mimeType andResponseEncoding:(NSStringEncodin #if NS_BLOCKS_AVAILABLE - (void)setStartedBlock:(ASIBasicBlock)aStartedBlock { - [startedBlock release]; startedBlock = [aStartedBlock copy]; } - (void)setHeadersReceivedBlock:(ASIHeadersBlock)aReceivedBlock { - [headersReceivedBlock release]; headersReceivedBlock = [aReceivedBlock copy]; } - (void)setCompletionBlock:(ASIBasicBlock)aCompletionBlock { - [completionBlock release]; completionBlock = [aCompletionBlock copy]; } - (void)setFailedBlock:(ASIBasicBlock)aFailedBlock { - [failureBlock release]; failureBlock = [aFailedBlock copy]; } - (void)setBytesReceivedBlock:(ASIProgressBlock)aBytesReceivedBlock { - [bytesReceivedBlock release]; bytesReceivedBlock = [aBytesReceivedBlock copy]; } - (void)setBytesSentBlock:(ASIProgressBlock)aBytesSentBlock { - [bytesSentBlock release]; bytesSentBlock = [aBytesSentBlock copy]; } - (void)setDownloadSizeIncrementedBlock:(ASISizeBlock)aDownloadSizeIncrementedBlock{ - [downloadSizeIncrementedBlock release]; downloadSizeIncrementedBlock = [aDownloadSizeIncrementedBlock copy]; } - (void)setUploadSizeIncrementedBlock:(ASISizeBlock)anUploadSizeIncrementedBlock { - [uploadSizeIncrementedBlock release]; uploadSizeIncrementedBlock = [anUploadSizeIncrementedBlock copy]; } - (void)setDataReceivedBlock:(ASIDataBlock)aReceivedBlock { - [dataReceivedBlock release]; dataReceivedBlock = [aReceivedBlock copy]; } - (void)setAuthenticationNeededBlock:(ASIBasicBlock)anAuthenticationBlock { - [authenticationNeededBlock release]; authenticationNeededBlock = [anAuthenticationBlock copy]; } - (void)setProxyAuthenticationNeededBlock:(ASIBasicBlock)aProxyAuthenticationBlock { - [proxyAuthenticationNeededBlock release]; proxyAuthenticationNeededBlock = [aProxyAuthenticationBlock copy]; } - (void)setRequestRedirectedBlock:(ASIBasicBlock)aRedirectBlock { - [requestRedirectedBlock release]; requestRedirectedBlock = [aRedirectBlock copy]; } #endif #pragma mark === -@synthesize username; -@synthesize password; -@synthesize userAgentString; -@synthesize domain; -@synthesize proxyUsername; -@synthesize proxyPassword; -@synthesize proxyDomain; -@synthesize url; -@synthesize originalURL; -@synthesize delegate; -@synthesize queue; -@synthesize uploadProgressDelegate; -@synthesize downloadProgressDelegate; @synthesize useKeychainPersistence; -@synthesize useSessionPersistence; -@synthesize useCookiePersistence; -@synthesize downloadDestinationPath; -@synthesize temporaryFileDownloadPath; -@synthesize temporaryUncompressedDataDownloadPath; -@synthesize didStartSelector; -@synthesize didReceiveResponseHeadersSelector; -@synthesize willRedirectSelector; -@synthesize didFinishSelector; -@synthesize didFailSelector; -@synthesize didReceiveDataSelector; -@synthesize authenticationRealm; -@synthesize proxyAuthenticationRealm; -@synthesize error; -@synthesize complete; -@synthesize requestHeaders; -@synthesize responseHeaders; -@synthesize responseCookies; -@synthesize requestCookies; -@synthesize requestCredentials; @synthesize responseStatusCode; -@synthesize rawResponseData; -@synthesize lastActivityTime; -@synthesize timeOutSeconds; -@synthesize requestMethod; -@synthesize postBody; @synthesize compressedPostBody; -@synthesize contentLength; @synthesize partialDownloadSize; @synthesize postLength; -@synthesize shouldResetDownloadProgress; -@synthesize shouldResetUploadProgress; -@synthesize mainRequest; -@synthesize totalBytesRead; -@synthesize totalBytesSent; -@synthesize showAccurateProgress; @synthesize uploadBufferSize; -@synthesize defaultResponseEncoding; @synthesize responseEncoding; -@synthesize allowCompressedResponse; @synthesize allowResumeForFileDownloads; -@synthesize userInfo; @synthesize tag; -@synthesize postBodyFilePath; -@synthesize compressedPostBodyFilePath; -@synthesize postBodyWriteStream; -@synthesize postBodyReadStream; -@synthesize shouldStreamPostDataFromDisk; -@synthesize didCreateTemporaryPostDataFile; @synthesize useHTTPVersionOne; @synthesize lastBytesRead; @synthesize lastBytesSent; -@synthesize cancelledLock; -@synthesize haveBuiltPostBody; @synthesize fileDownloadOutputStream; -@synthesize inflatedFileDownloadOutputStream; @synthesize authenticationRetryCount; @synthesize proxyAuthenticationRetryCount; @synthesize updatedProgress; -@synthesize shouldRedirect; -@synthesize validatesSecureCertificate; -@synthesize needsRedirect; @synthesize redirectCount; -@synthesize shouldCompressRequestBody; -@synthesize proxyCredentials; -@synthesize proxyHost; @synthesize proxyPort; -@synthesize proxyType; -@synthesize PACurl; -@synthesize authenticationScheme; -@synthesize proxyAuthenticationScheme; @synthesize shouldPresentAuthenticationDialog; -@synthesize shouldPresentProxyAuthenticationDialog; @synthesize authenticationNeeded; -@synthesize responseStatusMessage; -@synthesize shouldPresentCredentialsBeforeChallenge; @synthesize haveBuiltRequestHeaders; @synthesize inProgress; @synthesize numberOfTimesToRetryOnTimeout; @synthesize retryCount; @synthesize willRetryRequest; -@synthesize shouldAttemptPersistentConnection; -@synthesize persistentConnectionTimeoutSeconds; @synthesize connectionCanBeReused; -@synthesize connectionInfo; -@synthesize readStream; -@synthesize readStreamIsScheduled; @synthesize shouldUseRFC2616RedirectBehaviour; @synthesize downloadComplete; -@synthesize requestID; -@synthesize runLoopMode; -@synthesize statusTimer; -@synthesize downloadCache; @synthesize cachePolicy; @synthesize cacheStoragePolicy; @synthesize didUseCachedResponse; @synthesize secondsToCache; -@synthesize clientCertificates; -@synthesize redirectURL; #if TARGET_OS_IPHONE && __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_4_0 @synthesize shouldContinueWhenAppEntersBackground; #endif -@synthesize dataDecompressor; -@synthesize shouldWaitToInflateCompressedResponses; -@synthesize isPACFileRequest; @synthesize PACFileRequest; @synthesize PACFileReadStream; @synthesize PACFileData; diff --git a/Classes/ASIInputStream.h b/Classes/ASIInputStream.h index 7b9f93ed..e84cea00 100644 --- a/Classes/ASIInputStream.h +++ b/Classes/ASIInputStream.h @@ -14,13 +14,11 @@ // Subclassing NSInputStream seems to be tricky, and may involve overriding undocumented methods, so we'll cheat instead. // It is used by ASIHTTPRequest whenever we have a request body, and handles measuring and throttling the bandwidth used for uploading -@interface ASIInputStream : NSObject { - NSInputStream *stream; - ASIHTTPRequest *request; -} -+ (id)inputStreamWithFileAtPath:(NSString *)path request:(ASIHTTPRequest *)request; -+ (id)inputStreamWithData:(NSData *)data request:(ASIHTTPRequest *)request; +@interface ASIInputStream : NSObject -@property (retain, nonatomic) NSInputStream *stream; -@property (assign, nonatomic) ASIHTTPRequest *request; ++ (instancetype)inputStreamWithFileAtPath:(NSString *)path request:(ASIHTTPRequest *)request; ++ (instancetype)inputStreamWithData:(NSData *)data request:(ASIHTTPRequest *)request; + +@property (strong, nonatomic) NSInputStream *stream; +@property (weak, nonatomic) ASIHTTPRequest *request; @end diff --git a/Classes/ASIInputStream.m b/Classes/ASIInputStream.m index d2b84288..964e2296 100644 --- a/Classes/ASIInputStream.m +++ b/Classes/ASIInputStream.m @@ -21,28 +21,22 @@ + (void)initialize } } -+ (id)inputStreamWithFileAtPath:(NSString *)path request:(ASIHTTPRequest *)theRequest ++ (instancetype)inputStreamWithFileAtPath:(NSString *)path request:(ASIHTTPRequest *)theRequest { - ASIInputStream *theStream = [[[self alloc] init] autorelease]; + ASIInputStream *theStream = [[self alloc] init]; [theStream setRequest:theRequest]; [theStream setStream:[NSInputStream inputStreamWithFileAtPath:path]]; return theStream; } -+ (id)inputStreamWithData:(NSData *)data request:(ASIHTTPRequest *)theRequest ++ (instancetype)inputStreamWithData:(NSData *)data request:(ASIHTTPRequest *)theRequest { - ASIInputStream *theStream = [[[self alloc] init] autorelease]; + ASIInputStream *theStream = [[self alloc] init]; [theStream setRequest:theRequest]; [theStream setStream:[NSInputStream inputStreamWithData:data]]; return theStream; } -- (void)dealloc -{ - [stream release]; - [super dealloc]; -} - // Called when CFNetwork wants to read more of our request body // When throttling is on, we ask ASIHTTPRequest for the maximum amount of data we can read - (NSInteger)read:(uint8_t *)buffer maxLength:(NSUInteger)len @@ -56,10 +50,10 @@ - (NSInteger)read:(uint8_t *)buffer maxLength:(NSUInteger)len } else if (toRead == 0) { toRead = 1; } - [request performThrottling]; + [_request performThrottling]; } [readLock unlock]; - NSInteger rv = [stream read:buffer maxLength:toRead]; + NSInteger rv = [_stream read:buffer maxLength:toRead]; if (rv > 0) [ASIHTTPRequest incrementBandwidthUsedInLastSecond:rv]; return rv; @@ -72,52 +66,52 @@ - (NSInteger)read:(uint8_t *)buffer maxLength:(NSUInteger)len */ - (void)open { - [stream open]; + [_stream open]; } - (void)close { - [stream close]; + [_stream close]; } - (id)delegate { - return [stream delegate]; + return [_stream delegate]; } - (void)setDelegate:(id)delegate { - [stream setDelegate:delegate]; + [_stream setDelegate:delegate]; } - (void)scheduleInRunLoop:(NSRunLoop *)aRunLoop forMode:(NSString *)mode { - [stream scheduleInRunLoop:aRunLoop forMode:mode]; + [_stream scheduleInRunLoop:aRunLoop forMode:mode]; } - (void)removeFromRunLoop:(NSRunLoop *)aRunLoop forMode:(NSString *)mode { - [stream removeFromRunLoop:aRunLoop forMode:mode]; + [_stream removeFromRunLoop:aRunLoop forMode:mode]; } - (id)propertyForKey:(NSString *)key { - return [stream propertyForKey:key]; + return [_stream propertyForKey:key]; } - (BOOL)setProperty:(id)property forKey:(NSString *)key { - return [stream setProperty:property forKey:key]; + return [_stream setProperty:property forKey:key]; } - (NSStreamStatus)streamStatus { - return [stream streamStatus]; + return [_stream streamStatus]; } - (NSError *)streamError { - return [stream streamError]; + return [_stream streamError]; } // If we get asked to perform a method we don't have (probably internal ones), @@ -125,14 +119,12 @@ - (NSError *)streamError - (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector { - return [stream methodSignatureForSelector:aSelector]; + return [_stream methodSignatureForSelector:aSelector]; } - (void)forwardInvocation:(NSInvocation *)anInvocation { - [anInvocation invokeWithTarget:stream]; + [anInvocation invokeWithTarget:_stream]; } -@synthesize stream; -@synthesize request; @end diff --git a/Classes/ASINetworkQueue.h b/Classes/ASINetworkQueue.h index 787f391e..a156d071 100644 --- a/Classes/ASINetworkQueue.h +++ b/Classes/ASINetworkQueue.h @@ -12,63 +12,8 @@ @interface ASINetworkQueue : NSOperationQueue { - // Delegate will get didFail + didFinish messages (if set) - id delegate; - - // Will be called when a request starts with the request as the argument - SEL requestDidStartSelector; - - // Will be called when a request receives response headers - // Should take the form request:didRecieveResponseHeaders:, where the first argument is the request, and the second the headers dictionary - SEL requestDidReceiveResponseHeadersSelector; - - // Will be called when a request is about to redirect - // Should take the form request:willRedirectToURL:, where the first argument is the request, and the second the new url - SEL requestWillRedirectSelector; - - // Will be called when a request completes with the request as the argument - SEL requestDidFinishSelector; - - // Will be called when a request fails with the request as the argument - SEL requestDidFailSelector; - - // Will be called when the queue finishes with the queue as the argument - SEL queueDidFinishSelector; - - // Upload progress indicator, probably an NSProgressIndicator or UIProgressView - id uploadProgressDelegate; - - // Total amount uploaded so far for all requests in this queue - unsigned long long bytesUploadedSoFar; - - // Total amount to be uploaded for all requests in this queue - requests add to this figure as they work out how much data they have to transmit - unsigned long long totalBytesToUpload; - - // Download progress indicator, probably an NSProgressIndicator or UIProgressView - id downloadProgressDelegate; - - // Total amount downloaded so far for all requests in this queue - unsigned long long bytesDownloadedSoFar; - - // Total amount to be downloaded for all requests in this queue - requests add to this figure as they receive Content-Length headers - unsigned long long totalBytesToDownload; - - // When YES, the queue will cancel all requests when a request fails. Default is YES - BOOL shouldCancelAllRequestsOnFailure; - //Number of real requests (excludes HEAD requests created to manage showAccurateProgress) - int requestsCount; - - // When NO, this request will only update the progress indicator when it completes - // When YES, this request will update the progress indicator according to how much data it has received so far - // When YES, the queue will first perform HEAD requests for all GET requests in the queue, so it can calculate the total download size before it starts - // NO means better performance, because it skips this step for GET requests, and it won't waste time updating the progress indicator until a request completes - // Set to YES if the size of a requests in the queue varies greatly for much more accurate results - // Default for requests in the queue is NO - BOOL showAccurateProgress; - - // Storage container for additional queue information. - NSDictionary *userInfo; + int _requestsCount; } @@ -85,24 +30,63 @@ // This method will start the queue - (void)go; -@property (assign, nonatomic, setter=setUploadProgressDelegate:) id uploadProgressDelegate; -@property (assign, nonatomic, setter=setDownloadProgressDelegate:) id downloadProgressDelegate; +// Upload progress indicator, probably an NSProgressIndicator or UIProgressView +@property (weak, nonatomic, setter=setUploadProgressDelegate:) id uploadProgressDelegate; +// Download progress indicator, probably an NSProgressIndicator or UIProgressView +@property (weak, nonatomic, setter=setDownloadProgressDelegate:) id downloadProgressDelegate; + + +// Will be called when a request starts with the request as the argument @property (assign) SEL requestDidStartSelector; + +// Will be called when a request receives response headers +// Should take the form request:didRecieveResponseHeaders:, where the first argument is the request, and the second the headers dictionary @property (assign) SEL requestDidReceiveResponseHeadersSelector; + +// Will be called when a request is about to redirect +// Should take the form request:willRedirectToURL:, where the first argument is the request, and the second the new url @property (assign) SEL requestWillRedirectSelector; + +// Will be called when a request completes with the request as the argument @property (assign) SEL requestDidFinishSelector; + +// Will be called when a request fails with the request as the argument @property (assign) SEL requestDidFailSelector; + +// Will be called when the queue finishes with the queue as the argument @property (assign) SEL queueDidFinishSelector; + +// When YES, the queue will cancel all requests when a request fails. Default is YES @property (assign) BOOL shouldCancelAllRequestsOnFailure; -@property (assign) id delegate; + +// Delegate will get didFail + didFinish messages (if set) +@property (weak) id delegate; + +// When NO, this request will only update the progress indicator when it completes +// When YES, this request will update the progress indicator according to how much data it has received so far +// When YES, the queue will first perform HEAD requests for all GET requests in the queue, so it can calculate the total download size before it starts +// NO means better performance, because it skips this step for GET requests, and it won't waste time updating the progress indicator until a request completes +// Set to YES if the size of a requests in the queue varies greatly for much more accurate results +// Default for requests in the queue is NO @property (assign) BOOL showAccurateProgress; + +//Number of real requests (excludes HEAD requests created to manage showAccurateProgress) @property (assign, readonly) int requestsCount; + +// Storage container for additional queue information. @property (retain) NSDictionary *userInfo; +// Total amount uploaded so far for all requests in this queue @property (assign) unsigned long long bytesUploadedSoFar; + +// Total amount to be uploaded for all requests in this queue - requests add to this figure as they work out how much data they have to transmit @property (assign) unsigned long long totalBytesToUpload; + +// Total amount downloaded so far for all requests in this queue @property (assign) unsigned long long bytesDownloadedSoFar; + +// Total amount to be downloaded for all requests in this queue - requests add to this figure as they receive Content-Length headers @property (assign) unsigned long long totalBytesToDownload; @end diff --git a/Classes/ASINetworkQueue.m b/Classes/ASINetworkQueue.m index b24076db..38c1050a 100644 --- a/Classes/ASINetworkQueue.m +++ b/Classes/ASINetworkQueue.m @@ -9,10 +9,21 @@ #import "ASINetworkQueue.h" #import "ASIHTTPRequest.h" +#define ASISuppressPerformSelectorLeakWarning(Stuff) \ +do { \ +_Pragma("clang diagnostic push") \ +_Pragma("clang diagnostic ignored \"-Warc-performSelector-leaks\"") \ +Stuff \ +_Pragma("clang diagnostic pop") \ +} while (0) + // Private stuff @interface ASINetworkQueue () - - (void)resetProgressDelegate:(id *)progressDelegate; - @property (assign) int requestsCount; + +@property (assign) int requestsCount; + +- (void)resetProgressDelegate:(id)progressDelegate; + @end @implementation ASINetworkQueue @@ -29,7 +40,7 @@ - (id)init + (id)queue { - return [[[self alloc] init] autorelease]; + return [[self alloc] init]; } - (void)dealloc @@ -38,8 +49,6 @@ - (void)dealloc for (ASIHTTPRequest *request in [self operations]) { [request setQueue:nil]; } - [userInfo release]; - [super dealloc]; } - (void)setSuspended:(BOOL)suspend @@ -78,34 +87,34 @@ - (void)cancelAllOperations - (void)setUploadProgressDelegate:(id)newDelegate { - uploadProgressDelegate = newDelegate; - [self resetProgressDelegate:&uploadProgressDelegate]; + _uploadProgressDelegate = newDelegate; + [self resetProgressDelegate:_uploadProgressDelegate]; } - (void)setDownloadProgressDelegate:(id)newDelegate { - downloadProgressDelegate = newDelegate; - [self resetProgressDelegate:&downloadProgressDelegate]; + _downloadProgressDelegate = newDelegate; + [self resetProgressDelegate:_downloadProgressDelegate]; } -- (void)resetProgressDelegate:(id *)progressDelegate +- (void)resetProgressDelegate:(id)progressDelegate { #if !TARGET_OS_IPHONE // If the uploadProgressDelegate is an NSProgressIndicator, we set its MaxValue to 1.0 so we can treat it similarly to UIProgressViews SEL selector = @selector(setMaxValue:); - if ([*progressDelegate respondsToSelector:selector]) { + if ([progressDelegate respondsToSelector:selector]) { double max = 1.0; [ASIHTTPRequest performSelector:selector onTarget:progressDelegate withObject:nil amount:&max callerToRetain:nil]; } selector = @selector(setDoubleValue:); - if ([*progressDelegate respondsToSelector:selector]) { + if ([progressDelegate respondsToSelector:selector]) { double value = 0.0; [ASIHTTPRequest performSelector:selector onTarget:progressDelegate withObject:nil amount:&value callerToRetain:nil]; } #else SEL selector = @selector(setProgress:); - if ([*progressDelegate respondsToSelector:selector]) { + if ([progressDelegate respondsToSelector:selector]) { float value = 0.0f; [ASIHTTPRequest performSelector:selector onTarget:progressDelegate withObject:nil amount:&value callerToRetain:nil]; } @@ -153,7 +162,7 @@ - (void)addOperation:(NSOperation *)operation [self addHEADOperation:HEADRequest]; [request addDependency:HEADRequest]; if ([request shouldResetDownloadProgress]) { - [self resetProgressDelegate:&downloadProgressDelegate]; + [self resetProgressDelegate:_downloadProgressDelegate]; [request setShouldResetDownloadProgress:NO]; } } @@ -168,7 +177,7 @@ - (void)addOperation:(NSOperation *)operation } // Tell the request not to increment the upload size when it starts, as we've already added its length if ([request shouldResetUploadProgress]) { - [self resetProgressDelegate:&uploadProgressDelegate]; + [self resetProgressDelegate:_uploadProgressDelegate]; [request setShouldResetUploadProgress:NO]; } @@ -182,21 +191,27 @@ - (void)addOperation:(NSOperation *)operation - (void)requestStarted:(ASIHTTPRequest *)request { if ([self requestDidStartSelector]) { - [[self delegate] performSelector:[self requestDidStartSelector] withObject:request]; + ASISuppressPerformSelectorLeakWarning( + [[self delegate] performSelector:[self requestDidStartSelector] withObject:request]; + ); } } - (void)request:(ASIHTTPRequest *)request didReceiveResponseHeaders:(NSDictionary *)responseHeaders { if ([self requestDidReceiveResponseHeadersSelector]) { - [[self delegate] performSelector:[self requestDidReceiveResponseHeadersSelector] withObject:request withObject:responseHeaders]; + ASISuppressPerformSelectorLeakWarning( + [[self delegate] performSelector:[self requestDidReceiveResponseHeadersSelector] withObject:request withObject:responseHeaders]; + ); } } - (void)request:(ASIHTTPRequest *)request willRedirectToURL:(NSURL *)newURL { if ([self requestWillRedirectSelector]) { - [[self delegate] performSelector:[self requestWillRedirectSelector] withObject:request withObject:newURL]; + ASISuppressPerformSelectorLeakWarning( + [[self delegate] performSelector:[self requestWillRedirectSelector] withObject:request withObject:newURL]; + ); } } @@ -204,11 +219,15 @@ - (void)requestFinished:(ASIHTTPRequest *)request { [self setRequestsCount:[self requestsCount]-1]; if ([self requestDidFinishSelector]) { - [[self delegate] performSelector:[self requestDidFinishSelector] withObject:request]; + ASISuppressPerformSelectorLeakWarning( + [[self delegate] performSelector:[self requestDidFinishSelector] withObject:request]; + ); } if ([self requestsCount] == 0) { if ([self queueDidFinishSelector]) { - [[self delegate] performSelector:[self queueDidFinishSelector] withObject:self]; + ASISuppressPerformSelectorLeakWarning( + [[self delegate] performSelector:[self queueDidFinishSelector] withObject:self]; + ); } } } @@ -217,11 +236,15 @@ - (void)requestFailed:(ASIHTTPRequest *)request { [self setRequestsCount:[self requestsCount]-1]; if ([self requestDidFailSelector]) { - [[self delegate] performSelector:[self requestDidFailSelector] withObject:request]; + ASISuppressPerformSelectorLeakWarning( + [[self delegate] performSelector:[self requestDidFailSelector] withObject:request]; + ); } if ([self requestsCount] == 0) { if ([self queueDidFinishSelector]) { - [[self delegate] performSelector:[self queueDidFinishSelector] withObject:self]; + ASISuppressPerformSelectorLeakWarning( + [[self delegate] performSelector:[self queueDidFinishSelector] withObject:self]; + ); } } if ([self shouldCancelAllRequestsOnFailure] && [self requestsCount] > 0) { @@ -235,7 +258,7 @@ - (void)request:(ASIHTTPRequest *)request didReceiveBytes:(long long)bytes { [self setBytesDownloadedSoFar:[self bytesDownloadedSoFar]+bytes]; if ([self downloadProgressDelegate]) { - [ASIHTTPRequest updateProgressIndicator:&downloadProgressDelegate withProgress:[self bytesDownloadedSoFar] ofTotal:[self totalBytesToDownload]]; + [ASIHTTPRequest updateProgressIndicator:_downloadProgressDelegate withProgress:[self bytesDownloadedSoFar] ofTotal:[self totalBytesToDownload]]; } } @@ -243,7 +266,7 @@ - (void)request:(ASIHTTPRequest *)request didSendBytes:(long long)bytes { [self setBytesUploadedSoFar:[self bytesUploadedSoFar]+bytes]; if ([self uploadProgressDelegate]) { - [ASIHTTPRequest updateProgressIndicator:&uploadProgressDelegate withProgress:[self bytesUploadedSoFar] ofTotal:[self totalBytesToUpload]]; + [ASIHTTPRequest updateProgressIndicator:_uploadProgressDelegate withProgress:[self bytesUploadedSoFar] ofTotal:[self totalBytesToUpload]]; } } @@ -318,26 +341,8 @@ - (id)copyWithZone:(NSZone *)zone [newQueue setDownloadProgressDelegate:[self downloadProgressDelegate]]; [newQueue setShouldCancelAllRequestsOnFailure:[self shouldCancelAllRequestsOnFailure]]; [newQueue setShowAccurateProgress:[self showAccurateProgress]]; - [newQueue setUserInfo:[[[self userInfo] copyWithZone:zone] autorelease]]; + [newQueue setUserInfo:[[self userInfo] copyWithZone:zone]]; return newQueue; } - -@synthesize requestsCount; -@synthesize bytesUploadedSoFar; -@synthesize totalBytesToUpload; -@synthesize bytesDownloadedSoFar; -@synthesize totalBytesToDownload; -@synthesize shouldCancelAllRequestsOnFailure; -@synthesize uploadProgressDelegate; -@synthesize downloadProgressDelegate; -@synthesize requestDidStartSelector; -@synthesize requestDidReceiveResponseHeadersSelector; -@synthesize requestWillRedirectSelector; -@synthesize requestDidFinishSelector; -@synthesize requestDidFailSelector; -@synthesize queueDidFinishSelector; -@synthesize delegate; -@synthesize showAccurateProgress; -@synthesize userInfo; @end diff --git a/Classes/ASIWebPageRequest/ASIWebPageRequest.m b/Classes/ASIWebPageRequest/ASIWebPageRequest.m index eccac6a8..5cd96ffc 100644 --- a/Classes/ASIWebPageRequest/ASIWebPageRequest.m +++ b/Classes/ASIWebPageRequest/ASIWebPageRequest.m @@ -59,10 +59,6 @@ - (id)initWithURL:(NSURL *)newURL - (void)dealloc { [externalResourceQueue cancelAllOperations]; - [externalResourceQueue release]; - [resourceList release]; - [parentRequest release]; - [super dealloc]; } // This is a bit of a hack @@ -79,7 +75,7 @@ - (void)markAsFinished // Again, we call the super implementation in finishedFetchingExternalResources:, or here if this download was not an HTML or CSS file - (void)requestFinished { - complete = NO; + _complete = NO; if ([self mainRequest] || [self didUseCachedResponse]) { [super requestFinished]; [super markAsFinished]; @@ -322,7 +318,7 @@ - (void)finishedFetchingExternalResources:(ASINetworkQueue *)queue if ([self downloadDestinationPath]) { parsedResponse = [NSMutableString stringWithContentsOfFile:[self downloadDestinationPath] encoding:[self responseEncoding] error:&err]; } else { - parsedResponse = [[[self responseString] mutableCopy] autorelease]; + parsedResponse = [[self responseString] mutableCopy]; } if (err) { [self failWithError:[NSError errorWithDomain:NetworkRequestErrorDomain code:101 userInfo:[NSDictionary dictionaryWithObjectsAndKeys:@"Error: unable to read response CSS from disk",NSLocalizedDescriptionKey,nil]]]; @@ -360,7 +356,7 @@ - (void)finishedFetchingExternalResources:(ASINetworkQueue *)queue if ([self downloadDestinationPath]) { // Truncate the file first - [[[[NSFileManager alloc] init] autorelease] createFileAtPath:[self downloadDestinationPath] contents:nil attributes:nil]; + [[[NSFileManager alloc] init] createFileAtPath:[self downloadDestinationPath] contents:nil attributes:nil]; saveContext = xmlSaveToFd([[NSFileHandle fileHandleForWritingAtPath:[self downloadDestinationPath]] fileDescriptor],NULL,2); // 2 == XML_SAVE_NO_DECL, this isn't declared on Mac OS 10.5 xmlSaveDoc(saveContext, doc); @@ -380,14 +376,14 @@ - (void)finishedFetchingExternalResources:(ASINetworkQueue *)queue saveContext = xmlSaveToBuffer(buffer,NULL,2); // 2 == XML_SAVE_NO_DECL, this isn't declared on Mac OS 10.5 xmlSaveDoc(saveContext, doc); xmlSaveClose(saveContext); - [self setRawResponseData:[[[NSMutableData alloc] initWithBytes:buffer->content length:buffer->use] autorelease]]; + [self setRawResponseData:[[NSMutableData alloc] initWithBytes:buffer->content length:buffer->use]]; xmlBufferFree(buffer); #endif } // Strip the content encoding if the original response was gzipped if ([self isResponseCompressed]) { - NSMutableDictionary *headers = [[[self responseHeaders] mutableCopy] autorelease]; + NSMutableDictionary *headers = [[self responseHeaders] mutableCopy]; [headers removeObjectForKey:@"Content-Encoding"]; [self setResponseHeaders:headers]; } @@ -404,10 +400,10 @@ - (void)finishedFetchingExternalResources:(ASINetworkQueue *)queue } } if (![self parentRequest]) { - [[self class] updateProgressIndicator:&downloadProgressDelegate withProgress:contentLength ofTotal:contentLength]; + [[self class] updateProgressIndicator:[self downloadProgressDelegate] withProgress:[self contentLength] ofTotal:[self contentLength]]; } - NSMutableDictionary *newHeaders = [[[self responseHeaders] mutableCopy] autorelease]; + NSMutableDictionary *newHeaders = [[self responseHeaders] mutableCopy]; [newHeaders removeObjectForKey:@"Content-Encoding"]; [self setResponseHeaders:newHeaders]; @@ -584,11 +580,11 @@ - (BOOL)respondsToSelector:(SEL)selector } //Ok, now check for selectors we want to pass on to the delegate if (selector == @selector(requestStarted:) || selector == @selector(request:didReceiveResponseHeaders:) || selector == @selector(request:willRedirectToURL:) || selector == @selector(requestFinished:) || selector == @selector(requestFailed:) || selector == @selector(request:didReceiveData:) || selector == @selector(authenticationNeededForRequest:) || selector == @selector(proxyAuthenticationNeededForRequest:)) { - return [delegate respondsToSelector:selector]; + return [[self delegate] respondsToSelector:selector]; } else if (selector == @selector(request:didReceiveBytes:) || selector == @selector(request:incrementDownloadSizeBy:)) { - return [downloadProgressDelegate respondsToSelector:selector]; + return [[self downloadProgressDelegate] respondsToSelector:selector]; } else if (selector == @selector(request:didSendBytes:) || selector == @selector(request:incrementUploadSizeBy:)) { - return [uploadProgressDelegate respondsToSelector:selector]; + return [[self uploadProgressDelegate] respondsToSelector:selector]; } return [super respondsToSelector:selector]; } @@ -599,11 +595,11 @@ - (NSMethodSignature *)methodSignatureForSelector:(SEL)selector return [[self parentRequest] methodSignatureForSelector:selector]; } if (selector == @selector(requestStarted:) || selector == @selector(request:didReceiveResponseHeaders:) || selector == @selector(request:willRedirectToURL:) || selector == @selector(requestFinished:) || selector == @selector(requestFailed:) || selector == @selector(request:didReceiveData:) || selector == @selector(authenticationNeededForRequest:) || selector == @selector(proxyAuthenticationNeededForRequest:)) { - return [(id)delegate methodSignatureForSelector:selector]; + return [[(id)self delegate] methodSignatureForSelector:selector]; } else if (selector == @selector(request:didReceiveBytes:) || selector == @selector(request:incrementDownloadSizeBy:)) { - return [(id)downloadProgressDelegate methodSignatureForSelector:selector]; + return [[(id)self downloadProgressDelegate] methodSignatureForSelector:selector]; } else if (selector == @selector(request:didSendBytes:) || selector == @selector(request:incrementUploadSizeBy:)) { - return [(id)uploadProgressDelegate methodSignatureForSelector:selector]; + return [(id)[self uploadProgressDelegate] methodSignatureForSelector:selector]; } return nil; } @@ -615,11 +611,11 @@ - (void)forwardInvocation:(NSInvocation *)anInvocation } SEL selector = [anInvocation selector]; if (selector == @selector(requestStarted:) || selector == @selector(request:didReceiveResponseHeaders:) || selector == @selector(request:willRedirectToURL:) || selector == @selector(requestFinished:) || selector == @selector(requestFailed:) || selector == @selector(request:didReceiveData:) || selector == @selector(authenticationNeededForRequest:) || selector == @selector(proxyAuthenticationNeededForRequest:)) { - [anInvocation invokeWithTarget:delegate]; + [anInvocation invokeWithTarget:[self delegate]]; } else if (selector == @selector(request:didReceiveBytes:) || selector == @selector(request:incrementDownloadSizeBy:)) { - [anInvocation invokeWithTarget:downloadProgressDelegate]; + [anInvocation invokeWithTarget:[self downloadProgressDelegate]]; } else if (selector == @selector(request:didSendBytes:) || selector == @selector(request:incrementUploadSizeBy:)) { - [anInvocation invokeWithTarget:uploadProgressDelegate]; + [anInvocation invokeWithTarget:[self uploadProgressDelegate]]; } } diff --git a/Classes/Tests/ASICloudFilesRequestTests.m b/Classes/Tests/ASICloudFilesRequestTests.m index d0c459da..7230d8f9 100644 --- a/Classes/Tests/ASICloudFilesRequestTests.m +++ b/Classes/Tests/ASICloudFilesRequestTests.m @@ -257,13 +257,13 @@ - (void)testPostObject { ASICloudFilesObject *object = [ASICloudFilesObject object]; object.name = @"infotestfile.txt"; object.metadata = metadata; - + [metadata release]; + ASICloudFilesObjectRequest *request = [ASICloudFilesObjectRequest postObjectRequestWithContainer:@"ASICloudFilesTest" object:object]; [request startSynchronous]; GHAssertTrue([request responseStatusCode] == 202, @"Failed to post object metadata"); - [metadata release]; } diff --git a/Classes/Tests/ASIFormDataRequestTests.m b/Classes/Tests/ASIFormDataRequestTests.m index f54ef990..24c59b6f 100644 --- a/Classes/Tests/ASIFormDataRequestTests.m +++ b/Classes/Tests/ASIFormDataRequestTests.m @@ -70,7 +70,7 @@ - (void)testPostWithFileUpload [request setFile:path forKey:@"file"]; [request startSynchronous]; - BOOL success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"post_var: %@\r\npost_var2: %@\r\npost_var3: %@\r\nfile_name: %@\r\nfile_size: %hu\r\ncontent_type: %@",@"foo",d,v,@"bigfile",size,@"application/octet-stream"]]); + BOOL success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"post_var: %@\r\npost_var2: %@\r\npost_var3: %@\r\nfile_name: %@\r\nfile_size: %u\r\ncontent_type: %@",@"foo",d,v,@"bigfile",size,@"application/octet-stream"]]); GHAssertTrue(success,@"Failed to upload the correct data (using local file)"); //Try the same with the raw data @@ -81,7 +81,7 @@ - (void)testPostWithFileUpload [request setData:data forKey:@"file"]; [request startSynchronous]; - success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"post_var: %@\r\npost_var2: %@\r\npost_var3: %@\r\nfile_name: %@\r\nfile_size: %hu\r\ncontent_type: %@",@"foo",d,v,@"file",size,@"application/octet-stream"]]); + success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"post_var: %@\r\npost_var2: %@\r\npost_var3: %@\r\nfile_name: %@\r\nfile_size: %u\r\ncontent_type: %@",@"foo",d,v,@"file",size,@"application/octet-stream"]]); GHAssertTrue(success,@"Failed to upload the correct data (using NSData)"); //Post with custom content-type and file name @@ -92,7 +92,7 @@ - (void)testPostWithFileUpload [request setFile:path withFileName:@"myfile" andContentType:@"text/plain" forKey:@"file"]; [request startSynchronous]; - success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"post_var: %@\r\npost_var2: %@\r\npost_var3: %@\r\nfile_name: %@\r\nfile_size: %hu\r\ncontent_type: %@",@"foo",d,v,@"myfile",size,@"text/plain"]]); + success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"post_var: %@\r\npost_var2: %@\r\npost_var3: %@\r\nfile_name: %@\r\nfile_size: %u\r\ncontent_type: %@",@"foo",d,v,@"myfile",size,@"text/plain"]]); GHAssertTrue(success,@"Failed to send the correct content-type / file name"); //Post raw data with custom content-type and file name @@ -103,7 +103,7 @@ - (void)testPostWithFileUpload [request setData:data withFileName:@"myfile" andContentType:@"text/plain" forKey:@"file"]; [request startSynchronous]; - success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"post_var: %@\r\npost_var2: %@\r\npost_var3: %@\r\nfile_name: %@\r\nfile_size: %hu\r\ncontent_type: %@",@"foo",d,v,@"myfile",size,@"text/plain"]]); + success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"post_var: %@\r\npost_var2: %@\r\npost_var3: %@\r\nfile_name: %@\r\nfile_size: %u\r\ncontent_type: %@",@"foo",d,v,@"myfile",size,@"text/plain"]]); GHAssertTrue(success,@"Failed to send the correct content-type / file name"); } diff --git a/Classes/Tests/ASIHTTPRequestTests.m b/Classes/Tests/ASIHTTPRequestTests.m index d70df796..9362c4e6 100644 --- a/Classes/Tests/ASIHTTPRequestTests.m +++ b/Classes/Tests/ASIHTTPRequestTests.m @@ -436,15 +436,15 @@ - (void)testAutomaticRedirection if (i > 304 && i < 307) { continue; } - NSURL *url = [NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%hi",i]]; + NSURL *url = [NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%i",i]]; request = [ASIHTTPRequest requestWithURL:url]; [request setShouldRedirect:NO]; [request startSynchronous]; if (i == 304) { // 304s will not contain a body, as per rfc2616. Will test 304 handling in a future test when we have etag support continue; } - success = [[request responseString] isEqualToString:[NSString stringWithFormat:@"Non-redirected content with %hi status code",i]]; - GHAssertTrue(success,[NSString stringWithFormat:@"Got the wrong content when not redirecting after a %hi",i]); + success = [[request responseString] isEqualToString:[NSString stringWithFormat:@"Non-redirected content with %u status code",i]]; + GHAssertTrue(success,[NSString stringWithFormat:@"Got the wrong content when not redirecting after a %u",i]); request2 = [ASIFormDataRequest requestWithURL:url]; [request2 setPostValue:@"Giant Monkey" forKey:@"lookbehindyou"]; @@ -454,13 +454,13 @@ - (void)testAutomaticRedirection if (i>304) { method = @"POST"; } - NSString *expectedString = [NSString stringWithFormat:@"Redirected as %@ after a %hi status code",method,i]; + NSString *expectedString = [NSString stringWithFormat:@"Redirected as %@ after a %u status code",method,i]; if (i>304) { expectedString = [NSString stringWithFormat:@"%@\r\nWatch out for the Giant Monkey!",expectedString]; } success = [[request2 responseString] isEqualToString:expectedString]; - GHAssertTrue(success,[NSString stringWithFormat:@"Got the wrong content when redirecting after a %hi",i]); + GHAssertTrue(success,[NSString stringWithFormat:@"Got the wrong content when redirecting after a %u",i]); success = ([request2 responseStatusCode] == 200); GHAssertTrue(success,@"Got the wrong status code (expected 200)"); @@ -470,7 +470,7 @@ - (void)testAutomaticRedirection // Test RFC 2616 behaviour for (i=301; i<303; i++) { - NSURL *url = [NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%hi",i]]; + NSURL *url = [NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%u",i]]; request2 = [ASIFormDataRequest requestWithURL:url]; [request2 setPostValue:@"Giant Monkey" forKey:@"lookbehindyou"]; [request2 setShouldUseRFC2616RedirectBehaviour:YES]; @@ -483,14 +483,14 @@ - (void)testAutomaticRedirection success = ([request2 postLength] == 0 && ![request2 postBody] && [[request2 requestMethod] isEqualToString:@"GET"]); GHAssertTrue(success,@"Failed to reset request to GET on 303 redirect"); - success = [[request2 responseString] isEqualToString:[NSString stringWithFormat:@"Redirected as GET after a %hi status code",i]]; + success = [[request2 responseString] isEqualToString:[NSString stringWithFormat:@"Redirected as GET after a %u status code",i]]; GHAssertTrue(success,@"Failed to dump the post body on 303 redirect"); } else { success = ([request2 postLength] > 0 || ![request2 postBody] || ![[request2 requestMethod] isEqualToString:@"POST"]); GHAssertTrue(success,@"Failed to use the same request method and body for a redirect when using rfc2616 behaviour"); - success = ([[request2 responseString] isEqualToString:[NSString stringWithFormat:@"Redirected as POST after a %hi status code\r\nWatch out for the Giant Monkey!",i]]); + success = ([[request2 responseString] isEqualToString:[NSString stringWithFormat:@"Redirected as POST after a %u status code\r\nWatch out for the Giant Monkey!",i]]); GHAssertTrue(success,@"Failed to send the correct post body on redirect"); } } @@ -524,11 +524,11 @@ - (void)test30xCrash { int i; for (i=305; i<308; i++) { - ASIFormDataRequest *request = [ASIFormDataRequest requestWithURL:[NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%hi",i]]]; + ASIFormDataRequest *request = [ASIFormDataRequest requestWithURL:[NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%i",i]]]; [request setPostValue:@"foo" forKey:@"eep"]; [request setShouldRedirect:NO]; [request startSynchronous]; - request = [ASIFormDataRequest requestWithURL:[NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%hi",i]]]; + request = [ASIFormDataRequest requestWithURL:[NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%i",i]]]; [request setPostValue:@"foo" forKey:@"eep"]; [request startSynchronous]; } @@ -661,7 +661,7 @@ - (void)testUploadContentLength [request setPostBody:[NSMutableData dataWithLength:1024*32]]; [request startSynchronous]; - BOOL success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"%hu",(1024*32)]]); + BOOL success = ([[request responseString] isEqualToString:[NSString stringWithFormat:@"%d",(1024*32)]]); GHAssertTrue(success,@"Sent wrong content length"); } diff --git a/Classes/Tests/ASINetworkQueueTests.m b/Classes/Tests/ASINetworkQueueTests.m index 2fbee45e..d9697d2b 100755 --- a/Classes/Tests/ASINetworkQueueTests.m +++ b/Classes/Tests/ASINetworkQueueTests.m @@ -347,7 +347,7 @@ - (void)testUploadProgress int i; for (i=0; i<3; i++) { NSData *data = [[[NSMutableData alloc] initWithLength:fileSizes[i]*1024] autorelease]; - NSString *path = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"file%hi",i]]; + NSString *path = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"file%i",i]]; [data writeToFile:path atomically:NO]; ASIFormDataRequest *request = [[[ASIFormDataRequest alloc] initWithURL:url] autorelease]; [request setFile:path forKey:@"file"]; @@ -376,7 +376,7 @@ - (void)testUploadProgress for (i=0; i<3; i++) { NSData *data = [[[NSMutableData alloc] initWithLength:fileSizes[i]*1024] autorelease]; - NSString *path = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"file%hi",i]]; + NSString *path = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"file%i",i]]; [data writeToFile:path atomically:NO]; ASIFormDataRequest *request = [[[ASIFormDataRequest alloc] initWithURL:url] autorelease]; [request setFile:path forKey:@"file"]; diff --git a/Classes/Tests/ASIS3RequestTests.m b/Classes/Tests/ASIS3RequestTests.m index d747e01a..ba973a47 100644 --- a/Classes/Tests/ASIS3RequestTests.m +++ b/Classes/Tests/ASIS3RequestTests.m @@ -418,10 +418,10 @@ - (void)testListRequest // Firstly, create and upload 5 files int i; for (i=0; i<5; i++) { - NSString *text = [NSString stringWithFormat:@"This is the content of file #%hi",i]; - NSString *filePath = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"%hi.txt",i]]; + NSString *text = [NSString stringWithFormat:@"This is the content of file #%i",i]; + NSString *filePath = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"%i.txt",i]]; [[text dataUsingEncoding:NSUTF8StringEncoding] writeToFile:filePath atomically:NO]; - NSString *key = [NSString stringWithFormat:@"test-file/%hi",i]; + NSString *key = [NSString stringWithFormat:@"test-file/%i",i]; ASIS3ObjectRequest *request = [ASIS3ObjectRequest PUTRequestForFile:filePath withBucket:bucket key:key]; [request setSecretAccessKey:secretAccessKey]; [request setAccessKey:accessKey]; @@ -502,7 +502,7 @@ - (void)testListRequest i=0; // For each one, we'll just upload the same content again for (ASIS3BucketObject *object in [listRequest objects]) { - NSString *oldFilePath = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"%hi.txt",i]];; + NSString *oldFilePath = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"%i.txt",i]];; ASIS3Request *request = [object PUTRequestWithFile:oldFilePath]; [request setAccessKey:accessKey]; [request setSecretAccessKey:secretAccessKey]; @@ -641,7 +641,7 @@ - (void)testQueueProgress int i; for (i=0; i<5; i++) { - NSString *key = [NSString stringWithFormat:@"stuff/file%hi.txt",i+1]; + NSString *key = [NSString stringWithFormat:@"stuff/file%i.txt",i+1]; ASIS3ObjectRequest *s3Request = [ASIS3ObjectRequest PUTRequestForData:data withBucket:bucket key:key]; [s3Request setSecretAccessKey:secretAccessKey]; @@ -667,12 +667,12 @@ - (void)testQueueProgress for (i=0; i<5; i++) { - NSString *key = [NSString stringWithFormat:@"stuff/file%hi.txt",i+1]; + NSString *key = [NSString stringWithFormat:@"stuff/file%i.txt",i+1]; ASIS3ObjectRequest *s3Request = [ASIS3ObjectRequest requestWithBucket:bucket key:key]; [s3Request setSecretAccessKey:secretAccessKey]; [s3Request setAccessKey:accessKey]; - NSString *downloadPath = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"%hi.jpg",i+1]]; + NSString *downloadPath = [[self filePathForTemporaryTestFiles] stringByAppendingPathComponent:[NSString stringWithFormat:@"%i.jpg",i+1]]; [s3Request setDownloadDestinationPath:downloadPath]; [[self networkQueue] addOperation:s3Request]; } @@ -693,7 +693,7 @@ - (void)testQueueProgress for (i=0; i<5; i++) { - NSString *key = [NSString stringWithFormat:@"stuff/file%hi.txt",i+1]; + NSString *key = [NSString stringWithFormat:@"stuff/file%i.txt",i+1]; ASIS3ObjectRequest *s3Request = [ASIS3ObjectRequest DELETERequestWithBucket:bucket key:key]; [s3Request setSecretAccessKey:secretAccessKey]; diff --git a/External/Reachability/Reachability.h b/External/Reachability/Reachability.h deleted file mode 100644 index af524448..00000000 --- a/External/Reachability/Reachability.h +++ /dev/null @@ -1,194 +0,0 @@ -/* - - File: Reachability.h - Abstract: Basic demonstration of how to use the SystemConfiguration Reachablity APIs. - - Version: 2.0.4ddg - */ - -/* - Significant additions made by Andrew W. Donoho, August 11, 2009. - This is a derived work of Apple's Reachability v2.0 class. - - The below license is the new BSD license with the OSI recommended personalizations. - - - Extensions Copyright (C) 2009 Donoho Design Group, LLC. All Rights Reserved. - - Redistribution and use in source and binary forms, with or without - modification, are permitted provided that the following conditions are - met: - - * Redistributions of source code must retain the above copyright notice, - this list of conditions and the following disclaimer. - - * Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - - * Neither the name of Andrew W. Donoho nor Donoho Design Group, L.L.C. - may be used to endorse or promote products derived from this software - without specific prior written permission. - - THIS SOFTWARE IS PROVIDED BY DONOHO DESIGN GROUP, L.L.C. "AS IS" AND ANY - EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR - CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, - EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, - PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR - PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF - LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING - NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - - */ - - -/* - - Apple's Original License on Reachability v2.0 - - Disclaimer: IMPORTANT: This Apple software is supplied to you by Apple Inc. - ("Apple") in consideration of your agreement to the following terms, and your - use, installation, modification or redistribution of this Apple software - constitutes acceptance of these terms. If you do not agree with these terms, - please do not use, install, modify or redistribute this Apple software. - - In consideration of your agreement to abide by the following terms, and subject - to these terms, Apple grants you a personal, non-exclusive license, under - Apple's copyrights in this original Apple software (the "Apple Software"), to - use, reproduce, modify and redistribute the Apple Software, with or without - modifications, in source and/or binary forms; provided that if you redistribute - the Apple Software in its entirety and without modifications, you must retain - this notice and the following text and disclaimers in all such redistributions - of the Apple Software. - - Neither the name, trademarks, service marks or logos of Apple Inc. may be used - to endorse or promote products derived from the Apple Software without specific - prior written permission from Apple. Except as expressly stated in this notice, - no other rights or licenses, express or implied, are granted by Apple herein, - including but not limited to any patent rights that may be infringed by your - derivative works or by other works in which the Apple Software may be - incorporated. - - The Apple Software is provided by Apple on an "AS IS" basis. APPLE MAKES NO - WARRANTIES, EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION THE IMPLIED - WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY AND FITNESS FOR A PARTICULAR - PURPOSE, REGARDING THE APPLE SOFTWARE OR ITS USE AND OPERATION ALONE OR IN - COMBINATION WITH YOUR PRODUCTS. - - IN NO EVENT SHALL APPLE BE LIABLE FOR ANY SPECIAL, INDIRECT, INCIDENTAL OR - CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE - GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - ARISING IN ANY WAY OUT OF THE USE, REPRODUCTION, MODIFICATION AND/OR - DISTRIBUTION OF THE APPLE SOFTWARE, HOWEVER CAUSED AND WHETHER UNDER THEORY OF - CONTRACT, TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF - APPLE HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - - Copyright (C) 2009 Apple Inc. All Rights Reserved. - - */ - - -/* - DDG extensions include: - Each reachability object now has a copy of the key used to store it in a - dictionary. This allows each observer to quickly determine if the event is - important to them. - - -currentReachabilityStatus also has a significantly different decision criteria than - Apple's code. - - A multiple convenience test methods have been added. - */ - -#import -#import -#import - -#define USE_DDG_EXTENSIONS 1 // Use DDG's Extensions to test network criteria. -// Since NSAssert and NSCAssert are used in this code, -// I recommend you set NS_BLOCK_ASSERTIONS=1 in the release versions of your projects. - -enum { - - // DDG NetworkStatus Constant Names. - kNotReachable = 0, // Apple's code depends upon 'NotReachable' being the same value as 'NO'. - kReachableViaWWAN, // Switched order from Apple's enum. WWAN is active before WiFi. - kReachableViaWiFi - -}; -typedef uint32_t NetworkStatus; - -enum { - - // Apple NetworkStatus Constant Names. - NotReachable = kNotReachable, - ReachableViaWiFi = kReachableViaWiFi, - ReachableViaWWAN = kReachableViaWWAN - -}; - - -extern NSString *const kInternetConnection; -extern NSString *const kLocalWiFiConnection; -extern NSString *const kReachabilityChangedNotification; - -@interface Reachability: NSObject { - -@private - NSString *key_; - SCNetworkReachabilityRef reachabilityRef; - -} - -@property (copy) NSString *key; // Atomic because network operations are asynchronous. - -// Designated Initializer. -- (Reachability *) initWithReachabilityRef: (SCNetworkReachabilityRef) ref; - -// Use to check the reachability of a particular host name. -+ (Reachability *) reachabilityWithHostName: (NSString*) hostName; - -// Use to check the reachability of a particular IP address. -+ (Reachability *) reachabilityWithAddress: (const struct sockaddr_in*) hostAddress; - -// Use to check whether the default route is available. -// Should be used to, at minimum, establish network connectivity. -+ (Reachability *) reachabilityForInternetConnection; - -// Use to check whether a local wifi connection is available. -+ (Reachability *) reachabilityForLocalWiFi; - -//Start listening for reachability notifications on the current run loop. -- (BOOL) startNotifier; -- (void) stopNotifier; - -// Comparison routines to enable choosing actions in a notification. -- (BOOL) isEqual: (Reachability *) r; - -// These are the status tests. -- (NetworkStatus) currentReachabilityStatus; - -// The main direct test of reachability. -- (BOOL) isReachable; - -// WWAN may be available, but not active until a connection has been established. -// WiFi may require a connection for VPN on Demand. -- (BOOL) isConnectionRequired; // Identical DDG variant. -- (BOOL) connectionRequired; // Apple's routine. - -// Dynamic, on demand connection? -- (BOOL) isConnectionOnDemand; - -// Is user intervention required? -- (BOOL) isInterventionRequired; - -// Routines for specific connection testing by your app. -- (BOOL) isReachableViaWWAN; -- (BOOL) isReachableViaWiFi; - -- (SCNetworkReachabilityFlags) reachabilityFlags; - -@end diff --git a/External/Reachability/Reachability.m b/External/Reachability/Reachability.m deleted file mode 100644 index 51ba501d..00000000 --- a/External/Reachability/Reachability.m +++ /dev/null @@ -1,814 +0,0 @@ -/* - - File: Reachability.m - Abstract: Basic demonstration of how to use the SystemConfiguration Reachablity APIs. - - Version: 2.0.4ddg - */ - -/* - Significant additions made by Andrew W. Donoho, August 11, 2009. - This is a derived work of Apple's Reachability v2.0 class. - - The below license is the new BSD license with the OSI recommended personalizations. - - - Extensions Copyright (C) 2009 Donoho Design Group, LLC. All Rights Reserved. - - Redistribution and use in source and binary forms, with or without - modification, are permitted provided that the following conditions are - met: - - * Redistributions of source code must retain the above copyright notice, - this list of conditions and the following disclaimer. - - * Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - - * Neither the name of Andrew W. Donoho nor Donoho Design Group, L.L.C. - may be used to endorse or promote products derived from this software - without specific prior written permission. - - THIS SOFTWARE IS PROVIDED BY DONOHO DESIGN GROUP, L.L.C. "AS IS" AND ANY - EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR - CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, - EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, - PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR - PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF - LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING - NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - - */ - - -/* - - Apple's Original License on Reachability v2.0 - - Disclaimer: IMPORTANT: This Apple software is supplied to you by Apple Inc. - ("Apple") in consideration of your agreement to the following terms, and your - use, installation, modification or redistribution of this Apple software - constitutes acceptance of these terms. If you do not agree with these terms, - please do not use, install, modify or redistribute this Apple software. - - In consideration of your agreement to abide by the following terms, and subject - to these terms, Apple grants you a personal, non-exclusive license, under - Apple's copyrights in this original Apple software (the "Apple Software"), to - use, reproduce, modify and redistribute the Apple Software, with or without - modifications, in source and/or binary forms; provided that if you redistribute - the Apple Software in its entirety and without modifications, you must retain - this notice and the following text and disclaimers in all such redistributions - of the Apple Software. - - Neither the name, trademarks, service marks or logos of Apple Inc. may be used - to endorse or promote products derived from the Apple Software without specific - prior written permission from Apple. Except as expressly stated in this notice, - no other rights or licenses, express or implied, are granted by Apple herein, - including but not limited to any patent rights that may be infringed by your - derivative works or by other works in which the Apple Software may be - incorporated. - - The Apple Software is provided by Apple on an "AS IS" basis. APPLE MAKES NO - WARRANTIES, EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION THE IMPLIED - WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY AND FITNESS FOR A PARTICULAR - PURPOSE, REGARDING THE APPLE SOFTWARE OR ITS USE AND OPERATION ALONE OR IN - COMBINATION WITH YOUR PRODUCTS. - - IN NO EVENT SHALL APPLE BE LIABLE FOR ANY SPECIAL, INDIRECT, INCIDENTAL OR - CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE - GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - ARISING IN ANY WAY OUT OF THE USE, REPRODUCTION, MODIFICATION AND/OR - DISTRIBUTION OF THE APPLE SOFTWARE, HOWEVER CAUSED AND WHETHER UNDER THEORY OF - CONTRACT, TORT (INCLUDING NEGLIGENCE), STRICT LIABILITY OR OTHERWISE, EVEN IF - APPLE HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - - Copyright (C) 2009 Apple Inc. All Rights Reserved. - -*/ - -/* - Each reachability object now has a copy of the key used to store it in a dictionary. - This allows each observer to quickly determine if the event is important to them. -*/ - -#import -#import -#import -#import -#import -#import - -#import - -#import "Reachability.h" - -NSString *const kInternetConnection = @"InternetConnection"; -NSString *const kLocalWiFiConnection = @"LocalWiFiConnection"; -NSString *const kReachabilityChangedNotification = @"NetworkReachabilityChangedNotification"; - -#define CLASS_DEBUG 1 // Turn on logReachabilityFlags. Must also have a project wide defined DEBUG. - -#if (defined DEBUG && defined CLASS_DEBUG) -#define logReachabilityFlags(flags) (logReachabilityFlags_(__PRETTY_FUNCTION__, __LINE__, flags)) - -static NSString *reachabilityFlags_(SCNetworkReachabilityFlags flags) { - -#if (__IPHONE_OS_VERSION_MIN_REQUIRED >= 30000) // Apple advises you to use the magic number instead of a symbol. - return [NSString stringWithFormat:@"Reachability Flags: %c%c %c%c%c%c%c%c%c", - (flags & kSCNetworkReachabilityFlagsIsWWAN) ? 'W' : '-', - (flags & kSCNetworkReachabilityFlagsReachable) ? 'R' : '-', - - (flags & kSCNetworkReachabilityFlagsConnectionRequired) ? 'c' : '-', - (flags & kSCNetworkReachabilityFlagsTransientConnection) ? 't' : '-', - (flags & kSCNetworkReachabilityFlagsInterventionRequired) ? 'i' : '-', - (flags & kSCNetworkReachabilityFlagsConnectionOnTraffic) ? 'C' : '-', - (flags & kSCNetworkReachabilityFlagsConnectionOnDemand) ? 'D' : '-', - (flags & kSCNetworkReachabilityFlagsIsLocalAddress) ? 'l' : '-', - (flags & kSCNetworkReachabilityFlagsIsDirect) ? 'd' : '-']; -#else - // Compile out the v3.0 features for v2.2.1 deployment. - return [NSString stringWithFormat:@"Reachability Flags: %c%c %c%c%c%c%c%c", - (flags & kSCNetworkReachabilityFlagsIsWWAN) ? 'W' : '-', - (flags & kSCNetworkReachabilityFlagsReachable) ? 'R' : '-', - - (flags & kSCNetworkReachabilityFlagsConnectionRequired) ? 'c' : '-', - (flags & kSCNetworkReachabilityFlagsTransientConnection) ? 't' : '-', - (flags & kSCNetworkReachabilityFlagsInterventionRequired) ? 'i' : '-', - // v3 kSCNetworkReachabilityFlagsConnectionOnTraffic == v2 kSCNetworkReachabilityFlagsConnectionAutomatic - (flags & kSCNetworkReachabilityFlagsConnectionAutomatic) ? 'C' : '-', - // (flags & kSCNetworkReachabilityFlagsConnectionOnDemand) ? 'D' : '-', // No v2 equivalent. - (flags & kSCNetworkReachabilityFlagsIsLocalAddress) ? 'l' : '-', - (flags & kSCNetworkReachabilityFlagsIsDirect) ? 'd' : '-']; -#endif - -} // reachabilityFlags_() - -static void logReachabilityFlags_(const char *name, int line, SCNetworkReachabilityFlags flags) { - - NSLog(@"%s (%d) \n\t%@", name, line, reachabilityFlags_(flags)); - -} // logReachabilityFlags_() - -#define logNetworkStatus(status) (logNetworkStatus_(__PRETTY_FUNCTION__, __LINE__, status)) - -static void logNetworkStatus_(const char *name, int line, NetworkStatus status) { - - NSString *statusString = nil; - - switch (status) { - case kNotReachable: - statusString = @"Not Reachable"; - break; - case kReachableViaWWAN: - statusString = @"Reachable via WWAN"; - break; - case kReachableViaWiFi: - statusString = @"Reachable via WiFi"; - break; - } - - NSLog(@"%s (%d) \n\tNetwork Status: %@", name, line, statusString); - -} // logNetworkStatus_() - -#else -#define logReachabilityFlags(flags) -#define logNetworkStatus(status) -#endif - -@interface Reachability (private) - -- (NetworkStatus) networkStatusForFlags: (SCNetworkReachabilityFlags) flags; - -@end - -@implementation Reachability - -@synthesize key = key_; - -// Preclude direct access to ivars. -+ (BOOL) accessInstanceVariablesDirectly { - - return NO; - -} // accessInstanceVariablesDirectly - - -- (void) dealloc { - - [self stopNotifier]; - if(reachabilityRef) { - - CFRelease(reachabilityRef); reachabilityRef = NULL; - - } - - self.key = nil; - - [super dealloc]; - -} // dealloc - - -- (Reachability *) initWithReachabilityRef: (SCNetworkReachabilityRef) ref -{ - self = [super init]; - if (self != nil) - { - reachabilityRef = ref; - } - - return self; - -} // initWithReachabilityRef: - - -#if (defined DEBUG && defined CLASS_DEBUG) -- (NSString *) description { - - NSAssert(reachabilityRef, @"-description called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags = 0; - - SCNetworkReachabilityGetFlags(reachabilityRef, &flags); - - return [NSString stringWithFormat: @"%@\n\t%@", self.key, reachabilityFlags_(flags)]; - -} // description -#endif - - -#pragma mark - -#pragma mark Notification Management Methods - - -//Start listening for reachability notifications on the current run loop -static void ReachabilityCallback(SCNetworkReachabilityRef target, SCNetworkReachabilityFlags flags, void* info) { - - #pragma unused (target, flags) - NSCAssert(info, @"info was NULL in ReachabilityCallback"); - NSCAssert([(NSObject*) info isKindOfClass: [Reachability class]], @"info was the wrong class in ReachabilityCallback"); - - //We're on the main RunLoop, so an NSAutoreleasePool is not necessary, but is added defensively - // in case someone uses the Reachablity object in a different thread. - NSAutoreleasePool* pool = [NSAutoreleasePool new]; - - // Post a notification to notify the client that the network reachability changed. - [[NSNotificationCenter defaultCenter] postNotificationName: kReachabilityChangedNotification - object: (Reachability *) info]; - - [pool release]; - -} // ReachabilityCallback() - - -- (BOOL) startNotifier { - - SCNetworkReachabilityContext context = {0, self, NULL, NULL, NULL}; - - if(SCNetworkReachabilitySetCallback(reachabilityRef, ReachabilityCallback, &context)) { - - if(SCNetworkReachabilityScheduleWithRunLoop(reachabilityRef, CFRunLoopGetCurrent(), kCFRunLoopDefaultMode)) { - - return YES; - - } - - } - - return NO; - -} // startNotifier - - -- (void) stopNotifier { - - if(reachabilityRef) { - - SCNetworkReachabilityUnscheduleFromRunLoop(reachabilityRef, CFRunLoopGetCurrent(), kCFRunLoopDefaultMode); - - } - -} // stopNotifier - - -- (BOOL) isEqual: (Reachability *) r { - - return [r.key isEqualToString: self.key]; - -} // isEqual: - - -#pragma mark - -#pragma mark Reachability Allocation Methods - - -+ (Reachability *) reachabilityWithHostName: (NSString *) hostName { - - SCNetworkReachabilityRef ref = SCNetworkReachabilityCreateWithName(NULL, [hostName UTF8String]); - - if (ref) { - - Reachability *r = [[[self alloc] initWithReachabilityRef: ref] autorelease]; - - r.key = hostName; - - return r; - - } - - return nil; - -} // reachabilityWithHostName - - -+ (NSString *) makeAddressKey: (in_addr_t) addr { - // addr is assumed to be in network byte order. - - static const int highShift = 24; - static const int highMidShift = 16; - static const int lowMidShift = 8; - static const in_addr_t mask = 0x000000ff; - - addr = ntohl(addr); - - return [NSString stringWithFormat: @"%d.%d.%d.%d", - (addr >> highShift) & mask, - (addr >> highMidShift) & mask, - (addr >> lowMidShift) & mask, - addr & mask]; - -} // makeAddressKey: - - -+ (Reachability *) reachabilityWithAddress: (const struct sockaddr_in *) hostAddress { - - SCNetworkReachabilityRef ref = SCNetworkReachabilityCreateWithAddress(kCFAllocatorDefault, (const struct sockaddr*)hostAddress); - - if (ref) { - - Reachability *r = [[[self alloc] initWithReachabilityRef: ref] autorelease]; - - r.key = [self makeAddressKey: hostAddress->sin_addr.s_addr]; - - return r; - - } - - return nil; - -} // reachabilityWithAddress - - -+ (Reachability *) reachabilityForInternetConnection { - - struct sockaddr_in zeroAddress; - bzero(&zeroAddress, sizeof(zeroAddress)); - zeroAddress.sin_len = sizeof(zeroAddress); - zeroAddress.sin_family = AF_INET; - - Reachability *r = [self reachabilityWithAddress: &zeroAddress]; - - r.key = kInternetConnection; - - return r; - -} // reachabilityForInternetConnection - - -+ (Reachability *) reachabilityForLocalWiFi { - - struct sockaddr_in localWifiAddress; - bzero(&localWifiAddress, sizeof(localWifiAddress)); - localWifiAddress.sin_len = sizeof(localWifiAddress); - localWifiAddress.sin_family = AF_INET; - // IN_LINKLOCALNETNUM is defined in as 169.254.0.0 - localWifiAddress.sin_addr.s_addr = htonl(IN_LINKLOCALNETNUM); - - Reachability *r = [self reachabilityWithAddress: &localWifiAddress]; - - r.key = kLocalWiFiConnection; - - return r; - -} // reachabilityForLocalWiFi - - -#pragma mark - -#pragma mark Network Flag Handling Methods - - -#if USE_DDG_EXTENSIONS -// -// iPhone condition codes as reported by a 3GS running iPhone OS v3.0. -// Airplane Mode turned on: Reachability Flag Status: -- ------- -// WWAN Active: Reachability Flag Status: WR -t----- -// WWAN Connection required: Reachability Flag Status: WR ct----- -// WiFi turned on: Reachability Flag Status: -R ------- Reachable. -// Local WiFi turned on: Reachability Flag Status: -R xxxxxxd Reachable. -// WiFi turned on: Reachability Flag Status: -R ct----- Connection down. (Non-intuitive, empirically determined answer.) -const SCNetworkReachabilityFlags kConnectionDown = kSCNetworkReachabilityFlagsConnectionRequired | - kSCNetworkReachabilityFlagsTransientConnection; -// WiFi turned on: Reachability Flag Status: -R ct-i--- Reachable but it will require user intervention (e.g. enter a WiFi password). -// WiFi turned on: Reachability Flag Status: -R -t----- Reachable via VPN. -// -// In the below method, an 'x' in the flag status means I don't care about its value. -// -// This method differs from Apple's by testing explicitly for empirically observed values. -// This gives me more confidence in it's correct behavior. Apple's code covers more cases -// than mine. My code covers the cases that occur. -// -- (NetworkStatus) networkStatusForFlags: (SCNetworkReachabilityFlags) flags { - - if (flags & kSCNetworkReachabilityFlagsReachable) { - - // Local WiFi -- Test derived from Apple's code: -localWiFiStatusForFlags:. - if (self.key == kLocalWiFiConnection) { - - // Reachability Flag Status: xR xxxxxxd Reachable. - return (flags & kSCNetworkReachabilityFlagsIsDirect) ? kReachableViaWiFi : kNotReachable; - - } - - // Observed WWAN Values: - // WWAN Active: Reachability Flag Status: WR -t----- - // WWAN Connection required: Reachability Flag Status: WR ct----- - // - // Test Value: Reachability Flag Status: WR xxxxxxx - if (flags & kSCNetworkReachabilityFlagsIsWWAN) { return kReachableViaWWAN; } - - // Clear moot bits. - flags &= ~kSCNetworkReachabilityFlagsReachable; - flags &= ~kSCNetworkReachabilityFlagsIsDirect; - flags &= ~kSCNetworkReachabilityFlagsIsLocalAddress; // kInternetConnection is local. - - // Reachability Flag Status: -R ct---xx Connection down. - if (flags == kConnectionDown) { return kNotReachable; } - - // Reachability Flag Status: -R -t---xx Reachable. WiFi + VPN(is up) (Thank you Ling Wang) - if (flags & kSCNetworkReachabilityFlagsTransientConnection) { return kReachableViaWiFi; } - - // Reachability Flag Status: -R -----xx Reachable. - if (flags == 0) { return kReachableViaWiFi; } - - // Apple's code tests for dynamic connection types here. I don't. - // If a connection is required, regardless of whether it is on demand or not, it is a WiFi connection. - // If you care whether a connection needs to be brought up, use -isConnectionRequired. - // If you care about whether user intervention is necessary, use -isInterventionRequired. - // If you care about dynamically establishing the connection, use -isConnectionIsOnDemand. - - // Reachability Flag Status: -R cxxxxxx Reachable. - if (flags & kSCNetworkReachabilityFlagsConnectionRequired) { return kReachableViaWiFi; } - - // Required by the compiler. Should never get here. Default to not connected. -#if (defined DEBUG && defined CLASS_DEBUG) - NSAssert1(NO, @"Uncaught reachability test. Flags: %@", reachabilityFlags_(flags)); -#endif - return kNotReachable; - - } - - // Reachability Flag Status: x- xxxxxxx - return kNotReachable; - -} // networkStatusForFlags: - - -- (NetworkStatus) currentReachabilityStatus { - - NSAssert(reachabilityRef, @"currentReachabilityStatus called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags = 0; - NetworkStatus status = kNotReachable; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - -// logReachabilityFlags(flags); - - status = [self networkStatusForFlags: flags]; - - return status; - - } - - return kNotReachable; - -} // currentReachabilityStatus - - -- (BOOL) isReachable { - - NSAssert(reachabilityRef, @"isReachable called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags = 0; - NetworkStatus status = kNotReachable; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - -// logReachabilityFlags(flags); - - status = [self networkStatusForFlags: flags]; - -// logNetworkStatus(status); - - return (kNotReachable != status); - - } - - return NO; - -} // isReachable - - -- (BOOL) isConnectionRequired { - - NSAssert(reachabilityRef, @"isConnectionRequired called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - - logReachabilityFlags(flags); - - return (flags & kSCNetworkReachabilityFlagsConnectionRequired); - - } - - return NO; - -} // isConnectionRequired - - -- (BOOL) connectionRequired { - - return [self isConnectionRequired]; - -} // connectionRequired -#endif - - -#if (__IPHONE_OS_VERSION_MIN_REQUIRED >= 30000) -static const SCNetworkReachabilityFlags kOnDemandConnection = kSCNetworkReachabilityFlagsConnectionOnTraffic | - kSCNetworkReachabilityFlagsConnectionOnDemand; -#else -static const SCNetworkReachabilityFlags kOnDemandConnection = kSCNetworkReachabilityFlagsConnectionAutomatic; -#endif - -- (BOOL) isConnectionOnDemand { - - NSAssert(reachabilityRef, @"isConnectionIsOnDemand called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - - logReachabilityFlags(flags); - - return ((flags & kSCNetworkReachabilityFlagsConnectionRequired) && - (flags & kOnDemandConnection)); - - } - - return NO; - -} // isConnectionOnDemand - - -- (BOOL) isInterventionRequired { - - NSAssert(reachabilityRef, @"isInterventionRequired called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - - logReachabilityFlags(flags); - - return ((flags & kSCNetworkReachabilityFlagsConnectionRequired) && - (flags & kSCNetworkReachabilityFlagsInterventionRequired)); - - } - - return NO; - -} // isInterventionRequired - - -- (BOOL) isReachableViaWWAN { - - NSAssert(reachabilityRef, @"isReachableViaWWAN called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags = 0; - NetworkStatus status = kNotReachable; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - - logReachabilityFlags(flags); - - status = [self networkStatusForFlags: flags]; - - return (kReachableViaWWAN == status); - - } - - return NO; - -} // isReachableViaWWAN - - -- (BOOL) isReachableViaWiFi { - - NSAssert(reachabilityRef, @"isReachableViaWiFi called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags = 0; - NetworkStatus status = kNotReachable; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - - logReachabilityFlags(flags); - - status = [self networkStatusForFlags: flags]; - - return (kReachableViaWiFi == status); - - } - - return NO; - -} // isReachableViaWiFi - - -- (SCNetworkReachabilityFlags) reachabilityFlags { - - NSAssert(reachabilityRef, @"reachabilityFlags called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags = 0; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - - logReachabilityFlags(flags); - - return flags; - - } - - return 0; - -} // reachabilityFlags - - -#pragma mark - -#pragma mark Apple's Network Flag Handling Methods - - -#if !USE_DDG_EXTENSIONS -/* - * - * Apple's Network Status testing code. - * The only changes that have been made are to use the new logReachabilityFlags macro and - * test for local WiFi via the key instead of Apple's boolean. Also, Apple's code was for v3.0 only - * iPhone OS. v2.2.1 and earlier conditional compiling is turned on. Hence, to mirror Apple's behavior, - * set your Base SDK to v3.0 or higher. - * - */ - -- (NetworkStatus) localWiFiStatusForFlags: (SCNetworkReachabilityFlags) flags -{ - logReachabilityFlags(flags); - - BOOL retVal = NotReachable; - if((flags & kSCNetworkReachabilityFlagsReachable) && (flags & kSCNetworkReachabilityFlagsIsDirect)) - { - retVal = ReachableViaWiFi; - } - return retVal; -} - - -- (NetworkStatus) networkStatusForFlags: (SCNetworkReachabilityFlags) flags -{ - logReachabilityFlags(flags); - if (!(flags & kSCNetworkReachabilityFlagsReachable)) - { - // if target host is not reachable - return NotReachable; - } - - BOOL retVal = NotReachable; - - if (!(flags & kSCNetworkReachabilityFlagsConnectionRequired)) - { - // if target host is reachable and no connection is required - // then we'll assume (for now) that your on Wi-Fi - retVal = ReachableViaWiFi; - } - -#if (__IPHONE_OS_VERSION_MIN_REQUIRED >= 30000) // Apple advises you to use the magic number instead of a symbol. - if ((flags & kSCNetworkReachabilityFlagsConnectionOnDemand) || - (flags & kSCNetworkReachabilityFlagsConnectionOnTraffic)) -#else - if (flags & kSCNetworkReachabilityFlagsConnectionAutomatic) -#endif - { - // ... and the connection is on-demand (or on-traffic) if the - // calling application is using the CFSocketStream or higher APIs - - if (!(flags & kSCNetworkReachabilityFlagsInterventionRequired)) - { - // ... and no [user] intervention is needed - retVal = ReachableViaWiFi; - } - } - - if (flags & kSCNetworkReachabilityFlagsIsWWAN) - { - // ... but WWAN connections are OK if the calling application - // is using the CFNetwork (CFSocketStream?) APIs. - retVal = ReachableViaWWAN; - } - return retVal; -} - - -- (NetworkStatus) currentReachabilityStatus -{ - NSAssert(reachabilityRef, @"currentReachabilityStatus called with NULL reachabilityRef"); - - NetworkStatus retVal = NotReachable; - SCNetworkReachabilityFlags flags; - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) - { - if(self.key == kLocalWiFiConnection) - { - retVal = [self localWiFiStatusForFlags: flags]; - } - else - { - retVal = [self networkStatusForFlags: flags]; - } - } - return retVal; -} - - -- (BOOL) isReachable { - - NSAssert(reachabilityRef, @"isReachable called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags = 0; - NetworkStatus status = kNotReachable; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - - logReachabilityFlags(flags); - - if(self.key == kLocalWiFiConnection) { - - status = [self localWiFiStatusForFlags: flags]; - - } else { - - status = [self networkStatusForFlags: flags]; - - } - - return (kNotReachable != status); - - } - - return NO; - -} // isReachable - - -- (BOOL) isConnectionRequired { - - return [self connectionRequired]; - -} // isConnectionRequired - - -- (BOOL) connectionRequired { - - NSAssert(reachabilityRef, @"connectionRequired called with NULL reachabilityRef"); - - SCNetworkReachabilityFlags flags; - - if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) { - - logReachabilityFlags(flags); - - return (flags & kSCNetworkReachabilityFlagsConnectionRequired); - - } - - return NO; - -} // connectionRequired -#endif - -@end diff --git a/External/Reachability/_Reachability.h b/External/Reachability/_Reachability.h new file mode 100644 index 00000000..973c470b --- /dev/null +++ b/External/Reachability/_Reachability.h @@ -0,0 +1,109 @@ +/* + Copyright (c) 2011, Tony Million. + All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are met: + + 1. Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + + 2. Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + POSSIBILITY OF SUCH DAMAGE. + */ + +#import +#import + +#import +#import +#import +#import +#import +#import + +/** + * Does ARC support GCD objects? + * It does if the minimum deployment target is iOS 6+ or Mac OS X 8+ + * + * @see http://opensource.apple.com/source/libdispatch/libdispatch-228.18/os/object.h + **/ +#if OS_OBJECT_USE_OBJC +#define NEEDS_DISPATCH_RETAIN_RELEASE 0 +#else +#define NEEDS_DISPATCH_RETAIN_RELEASE 1 +#endif + +/** + * Create NS_ENUM macro if it does not exist on the targeted version of iOS or OS X. + * + * @see http://nshipster.com/ns_enum-ns_options/ + **/ +#ifndef NS_ENUM +#define NS_ENUM(_type, _name) enum _name : _type _name; enum _name : _type +#endif + +extern NSString *const kReachabilityChangedNotification; + +typedef NS_ENUM(NSInteger, NetworkStatus) { + // Apple NetworkStatus Compatible Names. + NotReachable = 0, + ReachableViaWiFi = 2, + ReachableViaWWAN = 1 +}; + +@class _Reachability; + +typedef void (^NetworkReachable)(_Reachability * reachability); +typedef void (^NetworkUnreachable)(_Reachability * reachability); + +@interface _Reachability : NSObject + +@property (nonatomic, copy) NetworkReachable reachableBlock; +@property (nonatomic, copy) NetworkUnreachable unreachableBlock; + + +@property (nonatomic, assign) BOOL reachableOnWWAN; + ++(_Reachability*)reachabilityWithHostname:(NSString*)hostname; ++(_Reachability*)reachabilityForInternetConnection; ++(_Reachability*)reachabilityWithAddress:(const struct sockaddr_in*)hostAddress; ++(_Reachability*)reachabilityForLocalWiFi; + +-(_Reachability *)initWithReachabilityRef:(SCNetworkReachabilityRef)ref; + +-(BOOL)startNotifier; +-(void)stopNotifier; + +-(BOOL)isReachable; +-(BOOL)isReachableViaWWAN; +-(BOOL)isReachableViaWiFi; + +// WWAN may be available, but not active until a connection has been established. +// WiFi may require a connection for VPN on Demand. +-(BOOL)isConnectionRequired; // Identical DDG variant. +-(BOOL)connectionRequired; // Apple's routine. +// Dynamic, on demand connection? +-(BOOL)isConnectionOnDemand; +// Is user intervention required? +-(BOOL)isInterventionRequired; + +-(NetworkStatus)currentReachabilityStatus; +-(SCNetworkReachabilityFlags)reachabilityFlags; +-(NSString*)currentReachabilityString; +-(NSString*)currentReachabilityFlags; + +@end diff --git a/External/Reachability/_Reachability.m b/External/Reachability/_Reachability.m new file mode 100644 index 00000000..88a180dc --- /dev/null +++ b/External/Reachability/_Reachability.m @@ -0,0 +1,527 @@ +/* + Copyright (c) 2011, Tony Million. + All rights reserved. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions are met: + + 1. Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + + 2. Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + POSSIBILITY OF SUCH DAMAGE. + */ + +#import "_Reachability.h" + + +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; + +-(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 + (flags & kSCNetworkReachabilityFlagsIsWWAN) ? 'W' : '-', +#else + 'X', +#endif + (flags & kSCNetworkReachabilityFlagsReachable) ? 'R' : '-', + (flags & kSCNetworkReachabilityFlagsConnectionRequired) ? 'c' : '-', + (flags & kSCNetworkReachabilityFlagsTransientConnection) ? 't' : '-', + (flags & kSCNetworkReachabilityFlagsInterventionRequired) ? 'i' : '-', + (flags & kSCNetworkReachabilityFlagsConnectionOnTraffic) ? 'C' : '-', + (flags & kSCNetworkReachabilityFlagsConnectionOnDemand) ? 'D' : '-', + (flags & kSCNetworkReachabilityFlagsIsLocalAddress) ? 'l' : '-', + (flags & kSCNetworkReachabilityFlagsIsDirect) ? 'd' : '-']; +} + +// Start listening for reachability notifications on the current run loop +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? + @autoreleasepool + { + [reachability reachabilityChanged:flags]; + } +} + + +@implementation _Reachability + +@synthesize reachabilityRef; +@synthesize reachabilitySerialQueue; + +@synthesize reachableOnWWAN; + +@synthesize reachableBlock; +@synthesize unreachableBlock; + +@synthesize reachabilityObject; + +#pragma mark - Class Constructor Methods + ++(_Reachability*)reachabilityWithHostName:(NSString*)hostname +{ + return [_Reachability reachabilityWithHostname:hostname]; +} + ++(_Reachability*)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 +{ + 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 +{ + struct sockaddr_in zeroAddress; + bzero(&zeroAddress, sizeof(zeroAddress)); + zeroAddress.sin_len = sizeof(zeroAddress); + zeroAddress.sin_family = AF_INET; + + return [self reachabilityWithAddress:&zeroAddress]; +} + ++(_Reachability*)reachabilityForLocalWiFi +{ + struct sockaddr_in localWifiAddress; + bzero(&localWifiAddress, sizeof(localWifiAddress)); + localWifiAddress.sin_len = sizeof(localWifiAddress); + localWifiAddress.sin_family = AF_INET; + // IN_LINKLOCALNETNUM is defined in as 169.254.0.0 + localWifiAddress.sin_addr.s_addr = htonl(IN_LINKLOCALNETNUM); + + return [self reachabilityWithAddress:&localWifiAddress]; +} + + +// Initialization methods + +-(_Reachability *)initWithReachabilityRef:(SCNetworkReachabilityRef)ref +{ + self = [super init]; + if (self != nil) + { + self.reachableOnWWAN = YES; + self.reachabilityRef = ref; + } + + return self; +} + +-(void)dealloc +{ + [self stopNotifier]; + + if(self.reachabilityRef) + { + CFRelease(self.reachabilityRef); + self.reachabilityRef = nil; + } + + self.reachableBlock = nil; + self.unreachableBlock = nil; + +#if !(__has_feature(objc_arc)) + [super dealloc]; +#endif + + +} + +#pragma mark - Notifier Methods + +// Notifier +// NOTE: This uses GCD to trigger the blocks - they *WILL NOT* be called on THE MAIN THREAD +// - In other words DO NOT DO ANY UI UPDATES IN THE BLOCKS. +// INSTEAD USE dispatch_async(dispatch_get_main_queue(), ^{UISTUFF}) (or dispatch_sync if you want) + +-(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) + { + return NO; + } + +#if __has_feature(objc_arc) + context.info = (__bridge void *)self; +#else + context.info = (void *)self; +#endif + + if (!SCNetworkReachabilitySetCallback(self.reachabilityRef, TMReachabilityCallback, &context)) + { +#ifdef DEBUG + NSLog(@"SCNetworkReachabilitySetCallback() 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; + } + + self.reachabilityObject = nil; + + return NO; + } + + // Set it as our reachability queue, which will retain the queue + if(!SCNetworkReachabilitySetDispatchQueue(self.reachabilityRef, self.reachabilitySerialQueue)) + { +#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); +#endif + self.reachabilitySerialQueue = nil; + } + + self.reachabilityObject = nil; + + return NO; + } + + return YES; +} + +-(void)stopNotifier +{ + // First stop, any callbacks! + SCNetworkReachabilitySetCallback(self.reachabilityRef, NULL, NULL); + + // 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; +} + +#pragma mark - reachability tests + +// This is for the case where you flick the airplane mode; +// you end up getting something like this: +//Reachability: WR ct----- +//Reachability: -- ------- +//Reachability: WR ct----- +//Reachability: -- ------- +// We treat this as 4 UNREACHABLE triggers - really apple should do better than this + +#define testcase (kSCNetworkReachabilityFlagsConnectionRequired | kSCNetworkReachabilityFlagsTransientConnection) + +-(BOOL)isReachableWithFlags:(SCNetworkReachabilityFlags)flags +{ + BOOL connectionUP = YES; + + if(!(flags & kSCNetworkReachabilityFlagsReachable)) + connectionUP = NO; + + if( (flags & testcase) == testcase ) + connectionUP = NO; + +#if TARGET_OS_IPHONE + if(flags & kSCNetworkReachabilityFlagsIsWWAN) + { + // We're on 3G. + if(!self.reachableOnWWAN) + { + // We don't want to connect when on 3G. + connectionUP = NO; + } + } +#endif + + return connectionUP; +} + +-(BOOL)isReachable +{ + SCNetworkReachabilityFlags flags; + + if(!SCNetworkReachabilityGetFlags(self.reachabilityRef, &flags)) + return NO; + + return [self isReachableWithFlags:flags]; +} + +-(BOOL)isReachableViaWWAN +{ +#if TARGET_OS_IPHONE + + SCNetworkReachabilityFlags flags = 0; + + if(SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + { + // Check we're REACHABLE + if(flags & kSCNetworkReachabilityFlagsReachable) + { + // Now, check we're on WWAN + if(flags & kSCNetworkReachabilityFlagsIsWWAN) + { + return YES; + } + } + } +#endif + + return NO; +} + +-(BOOL)isReachableViaWiFi +{ + SCNetworkReachabilityFlags flags = 0; + + if(SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + { + // Check we're reachable + if((flags & kSCNetworkReachabilityFlagsReachable)) + { +#if TARGET_OS_IPHONE + // Check we're NOT on WWAN + if((flags & kSCNetworkReachabilityFlagsIsWWAN)) + { + return NO; + } +#endif + return YES; + } + } + + return NO; +} + + +// WWAN may be available, but not active until a connection has been established. +// WiFi may require a connection for VPN on Demand. +-(BOOL)isConnectionRequired +{ + return [self connectionRequired]; +} + +-(BOOL)connectionRequired +{ + SCNetworkReachabilityFlags flags; + + if(SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + { + return (flags & kSCNetworkReachabilityFlagsConnectionRequired); + } + + return NO; +} + +// Dynamic, on demand connection? +-(BOOL)isConnectionOnDemand +{ + SCNetworkReachabilityFlags flags; + + if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + { + return ((flags & kSCNetworkReachabilityFlagsConnectionRequired) && + (flags & (kSCNetworkReachabilityFlagsConnectionOnTraffic | kSCNetworkReachabilityFlagsConnectionOnDemand))); + } + + return NO; +} + +// Is user intervention required? +-(BOOL)isInterventionRequired +{ + SCNetworkReachabilityFlags flags; + + if (SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + { + return ((flags & kSCNetworkReachabilityFlagsConnectionRequired) && + (flags & kSCNetworkReachabilityFlagsInterventionRequired)); + } + + return NO; +} + + +#pragma mark - reachability status stuff + +-(NetworkStatus)currentReachabilityStatus +{ + if([self isReachable]) + { + if([self isReachableViaWiFi]) + return ReachableViaWiFi; + +#if TARGET_OS_IPHONE + return ReachableViaWWAN; +#endif + } + + return NotReachable; +} + +-(SCNetworkReachabilityFlags)reachabilityFlags +{ + SCNetworkReachabilityFlags flags = 0; + + if(SCNetworkReachabilityGetFlags(reachabilityRef, &flags)) + { + return flags; + } + + return 0; +} + +-(NSString*)currentReachabilityString +{ + NetworkStatus temp = [self currentReachabilityStatus]; + + if(temp == reachableOnWWAN) + { + // Updated for the fact that we have CDMA phones now! + return NSLocalizedString(@"Cellular", @""); + } + if (temp == ReachableViaWiFi) + { + return NSLocalizedString(@"WiFi", @""); + } + + return NSLocalizedString(@"No Connection", @""); +} + +-(NSString*)currentReachabilityFlags +{ + return reachabilityFlags([self reachabilityFlags]); +} + +#pragma mark - Callback function calls this method + +-(void)reachabilityChanged:(SCNetworkReachabilityFlags)flags +{ + if([self isReachableWithFlags:flags]) + { + if(self.reachableBlock) + { + self.reachableBlock(self); + } + } + else + { + if(self.unreachableBlock) + { + self.unreachableBlock(self); + } + } + + // this makes sure the change notification happens on the MAIN THREAD + dispatch_async(dispatch_get_main_queue(), ^{ + [[NSNotificationCenter defaultCenter] postNotificationName:kReachabilityChangedNotification + object:self]; + }); +} + +#pragma mark - Debug Description + +- (NSString *) description +{ + NSString *description = [NSString stringWithFormat:@"<%@: %#x>", + NSStringFromClass([self class]), (unsigned int) self]; + return description; +} + +@end diff --git a/Mac.xcodeproj/project.pbxproj b/Mac.xcodeproj/project.pbxproj index 6ef6fb53..f914d4f0 100644 --- a/Mac.xcodeproj/project.pbxproj +++ b/Mac.xcodeproj/project.pbxproj @@ -63,6 +63,27 @@ B5BF64E612FDE9CA00CBC324 /* GHUnit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B5BF64E512FDE9C900CBC324 /* GHUnit.framework */; }; B5C664BC100A6220004F3C96 /* ASIS3RequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5C664BB100A6220004F3C96 /* ASIS3RequestTests.m */; }; B5ED5A9412FEBAEC00A12511 /* GHUnit.framework in CopyFiles */ = {isa = PBXBuildFile; fileRef = B5BF64E512FDE9C900CBC324 /* GHUnit.framework */; }; + C0DC558515A02A2C0007DB20 /* Cocoa.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C0DC558415A02A2C0007DB20 /* Cocoa.framework */; }; + C0DC559015A02A5E0007DB20 /* ASIHTTPRequestConfig.h in Headers */ = {isa = PBXBuildFile; fileRef = B551DD3310D6AB6B00EC1CBF /* ASIHTTPRequestConfig.h */; }; + C0DC559115A02A5E0007DB20 /* ASIProgressDelegate.h in Headers */ = {isa = PBXBuildFile; fileRef = B5747B3A11746CF500C9414E /* ASIProgressDelegate.h */; }; + C0DC559215A02A5E0007DB20 /* ASIHTTPRequestDelegate.h in Headers */ = {isa = PBXBuildFile; fileRef = B5747EA91174B1C100C9414E /* ASIHTTPRequestDelegate.h */; }; + C0DC559315A02A5E0007DB20 /* ASIInputStream.h in Headers */ = {isa = PBXBuildFile; fileRef = B522D71D103074AC009A2D22 /* ASIInputStream.h */; }; + C0DC559415A02A5E0007DB20 /* ASIInputStream.m in Sources */ = {isa = PBXBuildFile; fileRef = B522D71E103074AC009A2D22 /* ASIInputStream.m */; }; + C0DC559515A02A5E0007DB20 /* ASIFormDataRequest.h in Headers */ = {isa = PBXBuildFile; fileRef = B55B5D110F76568E0064029C /* ASIFormDataRequest.h */; }; + C0DC559615A02A5E0007DB20 /* ASIFormDataRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B5D120F76568E0064029C /* ASIFormDataRequest.m */; }; + C0DC559715A02A5E0007DB20 /* ASIHTTPRequest.h in Headers */ = {isa = PBXBuildFile; fileRef = B55B5D130F76568E0064029C /* ASIHTTPRequest.h */; }; + C0DC559815A02A5E0007DB20 /* ASIHTTPRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B5D140F76568E0064029C /* ASIHTTPRequest.m */; }; + C0DC559915A02A5E0007DB20 /* ASINetworkQueue.h in Headers */ = {isa = PBXBuildFile; fileRef = B55B5D150F76568E0064029C /* ASINetworkQueue.h */; }; + C0DC559A15A02A5E0007DB20 /* ASINetworkQueue.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B5D160F76568E0064029C /* ASINetworkQueue.m */; }; + C0DC559B15A02A5E0007DB20 /* ASICacheDelegate.h in Headers */ = {isa = PBXBuildFile; fileRef = B552535C11D23EBB00F9B170 /* ASICacheDelegate.h */; }; + C0DC559C15A02A5E0007DB20 /* ASIDownloadCache.h in Headers */ = {isa = PBXBuildFile; fileRef = B552535B11D23EBB00F9B170 /* ASIDownloadCache.h */; }; + C0DC559D15A02A5E0007DB20 /* ASIDownloadCache.m in Sources */ = {isa = PBXBuildFile; fileRef = B552535A11D23EBB00F9B170 /* ASIDownloadCache.m */; }; + C0DC559E15A02A5E0007DB20 /* ASIDataCompressor.h in Headers */ = {isa = PBXBuildFile; fileRef = B53E62701255ED8700C1E79A /* ASIDataCompressor.h */; }; + C0DC559F15A02A5E0007DB20 /* ASIDataCompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E626F1255ED8700C1E79A /* ASIDataCompressor.m */; }; + C0DC55A015A02A5E0007DB20 /* ASIDataDecompressor.h in Headers */ = {isa = PBXBuildFile; fileRef = B53E628E1255EE4B00C1E79A /* ASIDataDecompressor.h */; }; + C0DC55A115A02A5E0007DB20 /* ASIDataDecompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E628D1255EE4B00C1E79A /* ASIDataDecompressor.m */; }; + C0DC55DD15A032FA0007DB20 /* SystemConfiguration.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B53FADE70FF38B2A002E2DE6 /* SystemConfiguration.framework */; }; + C0DC55DE15A033020007DB20 /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = B551D5C613ED432B00607B74 /* libz.dylib */; }; /* End PBXBuildFile section */ /* Begin PBXCopyFilesBuildPhase section */ @@ -175,6 +196,9 @@ B5C664BA100A6220004F3C96 /* ASIS3RequestTests.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ASIS3RequestTests.h; sourceTree = ""; }; B5C664BB100A6220004F3C96 /* ASIS3RequestTests.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = ASIS3RequestTests.m; sourceTree = ""; }; B5E3858B0F76606B00FD7857 /* Tests-Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; name = "Tests-Info.plist"; path = "Mac Sample/Tests-Info.plist"; sourceTree = ""; }; + C0DC558315A02A2C0007DB20 /* ASIHTTPRequestOSX.dylib */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.dylib"; includeInIndex = 0; path = ASIHTTPRequestOSX.dylib; sourceTree = BUILT_PRODUCTS_DIR; }; + C0DC558415A02A2C0007DB20 /* Cocoa.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Cocoa.framework; path = System/Library/Frameworks/Cocoa.framework; sourceTree = SDKROOT; }; + C0DC558815A02A2C0007DB20 /* ASIHTTPRequestOSX-Prefix.pch */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "ASIHTTPRequestOSX-Prefix.pch"; sourceTree = ""; }; /* End PBXFileReference section */ /* Begin PBXFrameworksBuildPhase section */ @@ -202,6 +226,16 @@ ); runOnlyForDeploymentPostprocessing = 0; }; + C0DC558015A02A2C0007DB20 /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + C0DC55DE15A033020007DB20 /* libz.dylib in Frameworks */, + C0DC55DD15A032FA0007DB20 /* SystemConfiguration.framework in Frameworks */, + C0DC558515A02A2C0007DB20 /* Cocoa.framework in Frameworks */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; /* End PBXFrameworksBuildPhase section */ /* Begin PBXGroup section */ @@ -229,6 +263,7 @@ children = ( 8D1107320486CEB800E47090 /* Mac.app */, B55B5EDF0F7658C70064029C /* Unit Tests (GHUnit).app */, + C0DC558315A02A2C0007DB20 /* ASIHTTPRequestOSX.dylib */, ); name = Products; sourceTree = ""; @@ -239,6 +274,7 @@ B55B5D100F76568E0064029C /* Classes */, 29B97315FDCFA39411CA2CEA /* Other Sources */, 29B97317FDCFA39411CA2CEA /* Resources */, + C0DC558615A02A2C0007DB20 /* ASIHTTPRequest-OSX */, 29B97323FDCFA39411CA2CEA /* Frameworks */, 19C28FACFE9D520D11CA2CBB /* Products */, B53FADE70FF38B2A002E2DE6 /* SystemConfiguration.framework */, @@ -280,6 +316,7 @@ isa = PBXGroup; children = ( 1058C7A0FEA54F0111CA2CBB /* Linked Frameworks */, + C0DC558415A02A2C0007DB20 /* Cocoa.framework */, 1058C7A2FEA54F0111CA2CBB /* Other Frameworks */, ); name = Frameworks; @@ -396,8 +433,45 @@ path = CloudFiles; sourceTree = ""; }; + C0DC558615A02A2C0007DB20 /* ASIHTTPRequest-OSX */ = { + isa = PBXGroup; + children = ( + C0DC558715A02A2C0007DB20 /* Supporting Files */, + ); + path = "ASIHTTPRequest-OSX"; + sourceTree = ""; + }; + C0DC558715A02A2C0007DB20 /* Supporting Files */ = { + isa = PBXGroup; + children = ( + C0DC558815A02A2C0007DB20 /* ASIHTTPRequestOSX-Prefix.pch */, + ); + name = "Supporting Files"; + sourceTree = ""; + }; /* End PBXGroup section */ +/* Begin PBXHeadersBuildPhase section */ + C0DC558115A02A2C0007DB20 /* Headers */ = { + isa = PBXHeadersBuildPhase; + buildActionMask = 2147483647; + files = ( + C0DC559015A02A5E0007DB20 /* ASIHTTPRequestConfig.h in Headers */, + C0DC559115A02A5E0007DB20 /* ASIProgressDelegate.h in Headers */, + C0DC559215A02A5E0007DB20 /* ASIHTTPRequestDelegate.h in Headers */, + C0DC559315A02A5E0007DB20 /* ASIInputStream.h in Headers */, + C0DC559515A02A5E0007DB20 /* ASIFormDataRequest.h in Headers */, + C0DC559715A02A5E0007DB20 /* ASIHTTPRequest.h in Headers */, + C0DC559915A02A5E0007DB20 /* ASINetworkQueue.h in Headers */, + C0DC559B15A02A5E0007DB20 /* ASICacheDelegate.h in Headers */, + C0DC559C15A02A5E0007DB20 /* ASIDownloadCache.h in Headers */, + C0DC559E15A02A5E0007DB20 /* ASIDataCompressor.h in Headers */, + C0DC55A015A02A5E0007DB20 /* ASIDataDecompressor.h in Headers */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXHeadersBuildPhase section */ + /* Begin PBXNativeTarget section */ 8D1107260486CEB800E47090 /* Mac */ = { isa = PBXNativeTarget; @@ -437,6 +511,23 @@ productReference = B55B5EDF0F7658C70064029C /* Unit Tests (GHUnit).app */; productType = "com.apple.product-type.application"; }; + C0DC558215A02A2C0007DB20 /* ASIHTTPRequestOSX */ = { + isa = PBXNativeTarget; + buildConfigurationList = C0DC558E15A02A2C0007DB20 /* Build configuration list for PBXNativeTarget "ASIHTTPRequestOSX" */; + buildPhases = ( + C0DC557F15A02A2C0007DB20 /* Sources */, + C0DC558015A02A2C0007DB20 /* Frameworks */, + C0DC558115A02A2C0007DB20 /* Headers */, + ); + buildRules = ( + ); + dependencies = ( + ); + name = ASIHTTPRequestOSX; + productName = ASIHTTPRequest; + productReference = C0DC558315A02A2C0007DB20 /* ASIHTTPRequestOSX.dylib */; + productType = "com.apple.product-type.library.dynamic"; + }; /* End PBXNativeTarget section */ /* Begin PBXProject section */ @@ -461,6 +552,7 @@ targets = ( 8D1107260486CEB800E47090 /* Mac */, B55B5EDE0F7658C70064029C /* Unit Tests (GHUnit) */, + C0DC558215A02A2C0007DB20 /* ASIHTTPRequestOSX */, ); }; /* End PBXProject section */ @@ -572,6 +664,20 @@ ); runOnlyForDeploymentPostprocessing = 0; }; + C0DC557F15A02A2C0007DB20 /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + C0DC559415A02A5E0007DB20 /* ASIInputStream.m in Sources */, + C0DC559615A02A5E0007DB20 /* ASIFormDataRequest.m in Sources */, + C0DC559815A02A5E0007DB20 /* ASIHTTPRequest.m in Sources */, + C0DC559A15A02A5E0007DB20 /* ASINetworkQueue.m in Sources */, + C0DC559D15A02A5E0007DB20 /* ASIDownloadCache.m in Sources */, + C0DC559F15A02A5E0007DB20 /* ASIDataCompressor.m in Sources */, + C0DC55A115A02A5E0007DB20 /* ASIDataDecompressor.m in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; /* End PBXSourcesBuildPhase section */ /* Begin PBXVariantGroup section */ @@ -727,6 +833,55 @@ }; name = Release; }; + C0DC558C15A02A2C0007DB20 /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + ARCHS = "$(ARCHS_STANDARD_64_BIT)"; + COPY_PHASE_STRIP = NO; + DYLIB_COMPATIBILITY_VERSION = 1; + DYLIB_CURRENT_VERSION = 1; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_DYNAMIC_NO_PIC = NO; + GCC_ENABLE_OBJC_EXCEPTIONS = YES; + GCC_PRECOMPILE_PREFIX_HEADER = YES; + GCC_PREFIX_HEADER = "ASIHTTPRequest-OSX/ASIHTTPRequestOSX-Prefix.pch"; + GCC_PREPROCESSOR_DEFINITIONS = ( + "DEBUG=1", + "$(inherited)", + ); + GCC_SYMBOLS_PRIVATE_EXTERN = NO; + GCC_VERSION = com.apple.compilers.llvm.clang.1_0; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES; + INSTALL_PATH = "@rpath"; + MACOSX_DEPLOYMENT_TARGET = 10.7; + PRODUCT_NAME = "$(TARGET_NAME)"; + }; + name = Debug; + }; + C0DC558D15A02A2C0007DB20 /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + ARCHS = "$(ARCHS_STANDARD_64_BIT)"; + COPY_PHASE_STRIP = YES; + DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; + DYLIB_COMPATIBILITY_VERSION = 1; + DYLIB_CURRENT_VERSION = 1; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_ENABLE_OBJC_EXCEPTIONS = YES; + GCC_PRECOMPILE_PREFIX_HEADER = YES; + GCC_PREFIX_HEADER = "ASIHTTPRequest-OSX/ASIHTTPRequestOSX-Prefix.pch"; + GCC_VERSION = com.apple.compilers.llvm.clang.1_0; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES; + INSTALL_PATH = "@rpath"; + MACOSX_DEPLOYMENT_TARGET = 10.7; + PRODUCT_NAME = "$(TARGET_NAME)"; + }; + name = Release; + }; /* End XCBuildConfiguration section */ /* Begin XCConfigurationList section */ @@ -757,6 +912,14 @@ defaultConfigurationIsVisible = 0; defaultConfigurationName = Release; }; + C0DC558E15A02A2C0007DB20 /* Build configuration list for PBXNativeTarget "ASIHTTPRequestOSX" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + C0DC558C15A02A2C0007DB20 /* Debug */, + C0DC558D15A02A2C0007DB20 /* Release */, + ); + defaultConfigurationIsVisible = 0; + }; /* End XCConfigurationList section */ }; rootObject = 29B97313FDCFA39411CA2CEA /* Project object */; diff --git a/README.textile b/README.textile index 7fe1f908..27567448 100644 --- a/README.textile +++ b/README.textile @@ -27,6 +27,6 @@ It provides: * Get notifications about changes in your request state via delegation or [NEW] blocks (Mac OS X 10.6, iOS 4 and above) * Comes with a broad range of unit tests -ASIHTTPRequest is compatible with Mac OS 10.5 or later, and iOS 3.0 or later. +ASIHTTPRequest is compatible with Mac OS 10.6 or later, and iOS 6.0 or later. Documentation is available "here":http://allseeing-i.com/ASIHTTPRequest. \ No newline at end of file diff --git a/de.lproj/ASIHTTPLocalizable.strings b/de.lproj/ASIHTTPLocalizable.strings new file mode 100644 index 00000000..c32a8872 --- /dev/null +++ b/de.lproj/ASIHTTPLocalizable.strings @@ -0,0 +1,13 @@ +/* + ASIHTTPLocalizable.strings + iPhone + + Created by Stefan on 04.06.14. + +*/ +"The request timed out" = "Zeitüberschreitung"; +"The request timed out" = "Zeitüberschreitung"; +"Authentication needed" = "Eine Authentifikation wird benötigt"; +"The request was cancelled" = "Abbruch durch Benutzer"; +"Unable to create request (bad url?)" = "Die Anfrage konnte nicht durchgeführt werden (fehlerhafte URL?)"; +"The request failed because it redirected too many times" = "Die Anfrage ist fehlgeschlagen, da sie zu oft weitergeleitet wurde."; diff --git a/en.lproj/ASIHTTPLocalizable.strings b/en.lproj/ASIHTTPLocalizable.strings new file mode 100644 index 00000000..e4a3161a --- /dev/null +++ b/en.lproj/ASIHTTPLocalizable.strings @@ -0,0 +1,7 @@ +/* + ASIHTTPLocalizable.strings + iPhone + + Created by Stefan on 04.06.14. + +*/ diff --git a/iPhone.xcodeproj/project.pbxproj b/iPhone.xcodeproj/project.pbxproj index 6863d2d5..f6e72c55 100644 --- a/iPhone.xcodeproj/project.pbxproj +++ b/iPhone.xcodeproj/project.pbxproj @@ -7,52 +7,52 @@ objects = { /* Begin PBXBuildFile section */ - B50C1823121C26DB0055FCAB /* ClientCertificateTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B50C1822121C26DB0055FCAB /* ClientCertificateTests.m */; }; + B50C1823121C26DB0055FCAB /* ClientCertificateTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B50C1822121C26DB0055FCAB /* ClientCertificateTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B50C182C121C26FA0055FCAB /* Security.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B50C182B121C26FA0055FCAB /* Security.framework */; }; B50C1848121C27510055FCAB /* client.p12 in Resources */ = {isa = PBXBuildFile; fileRef = B50C1847121C27510055FCAB /* client.p12 */; }; - B50D532C126C87ED0022EA6F /* BlocksTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B50D532B126C87ED0022EA6F /* BlocksTests.m */; }; + B50D532C126C87ED0022EA6F /* BlocksTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B50D532B126C87ED0022EA6F /* BlocksTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B50F66191297FA45003887B1 /* strict.xcconfig in Resources */ = {isa = PBXBuildFile; fileRef = B50F66181297FA45003887B1 /* strict.xcconfig */; }; B50F661A1297FA45003887B1 /* strict.xcconfig in Resources */ = {isa = PBXBuildFile; fileRef = B50F66181297FA45003887B1 /* strict.xcconfig */; }; B50F661B1297FA45003887B1 /* strict.xcconfig in Resources */ = {isa = PBXBuildFile; fileRef = B50F66181297FA45003887B1 /* strict.xcconfig */; }; - B51791A31024C3E800583567 /* AuthenticationViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B51791A21024C3E800583567 /* AuthenticationViewController.m */; }; - B51A1A9B11DDF85100ED75CF /* ASIDownloadCacheTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B51A1A7A11DDF7BF00ED75CF /* ASIDownloadCacheTests.m */; }; + B51791A31024C3E800583567 /* AuthenticationViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B51791A21024C3E800583567 /* AuthenticationViewController.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B51A1A9B11DDF85100ED75CF /* ASIDownloadCacheTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B51A1A7A11DDF7BF00ED75CF /* ASIDownloadCacheTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B522DACE1030B2AB009A2D22 /* ASIInputStream.m in Sources */ = {isa = PBXBuildFile; fileRef = B522DACD1030B2AB009A2D22 /* ASIInputStream.m */; }; B522DACF1030B2AB009A2D22 /* ASIInputStream.m in Sources */ = {isa = PBXBuildFile; fileRef = B522DACD1030B2AB009A2D22 /* ASIInputStream.m */; }; B523254211CA01F1006C6E5A /* Sample.xib in Resources */ = {isa = PBXBuildFile; fileRef = B523254111CA01F1006C6E5A /* Sample.xib */; }; B523254311CA01F1006C6E5A /* Sample.xib in Resources */ = {isa = PBXBuildFile; fileRef = B523254111CA01F1006C6E5A /* Sample.xib */; }; B52325AD11CA05A8006C6E5A /* info.png in Resources */ = {isa = PBXBuildFile; fileRef = B52325AC11CA05A8006C6E5A /* info.png */; }; - B5254FF91025F9BF00CF7BC4 /* ProxyTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5254FF71025F9BF00CF7BC4 /* ProxyTests.m */; }; - B52D4A2F10DA4ED5008E8365 /* PerformanceTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B52D4A2E10DA4ED5008E8365 /* PerformanceTests.m */; }; + B5254FF91025F9BF00CF7BC4 /* ProxyTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5254FF71025F9BF00CF7BC4 /* ProxyTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B52D4A2F10DA4ED5008E8365 /* PerformanceTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B52D4A2E10DA4ED5008E8365 /* PerformanceTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B53E6D951257B45800C1E79A /* ASIDataDecompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E6D911257B45800C1E79A /* ASIDataDecompressor.m */; }; B53E6D961257B45800C1E79A /* ASIDataCompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E6D931257B45800C1E79A /* ASIDataCompressor.m */; }; B53E6D971257B45800C1E79A /* ASIDataDecompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E6D911257B45800C1E79A /* ASIDataDecompressor.m */; }; B53E6D981257B45800C1E79A /* ASIDataCompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E6D931257B45800C1E79A /* ASIDataCompressor.m */; }; B53E6D991257B45800C1E79A /* ASIDataDecompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E6D911257B45800C1E79A /* ASIDataDecompressor.m */; }; B53E6D9A1257B45800C1E79A /* ASIDataCompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E6D931257B45800C1E79A /* ASIDataCompressor.m */; }; - B540400B115114BA00D8BE63 /* ASIS3Bucket.m in Sources */ = {isa = PBXBuildFile; fileRef = B5404000115114BA00D8BE63 /* ASIS3Bucket.m */; }; - B540400C115114BA00D8BE63 /* ASIS3BucketRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5404002115114BA00D8BE63 /* ASIS3BucketRequest.m */; }; - B540400D115114BA00D8BE63 /* ASIS3ObjectRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5404004115114BA00D8BE63 /* ASIS3ObjectRequest.m */; }; - B540400E115114BA00D8BE63 /* ASIS3ServiceRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5404006115114BA00D8BE63 /* ASIS3ServiceRequest.m */; }; - B55252B411D22E2200F9B170 /* Reachability.m in Sources */ = {isa = PBXBuildFile; fileRef = B55252B311D22E2200F9B170 /* Reachability.m */; }; - B55252B511D22E2200F9B170 /* Reachability.m in Sources */ = {isa = PBXBuildFile; fileRef = B55252B311D22E2200F9B170 /* Reachability.m */; }; - B55252B611D22E2200F9B170 /* Reachability.m in Sources */ = {isa = PBXBuildFile; fileRef = B55252B311D22E2200F9B170 /* Reachability.m */; }; + B540400B115114BA00D8BE63 /* ASIS3Bucket.m in Sources */ = {isa = PBXBuildFile; fileRef = B5404000115114BA00D8BE63 /* ASIS3Bucket.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B540400C115114BA00D8BE63 /* ASIS3BucketRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5404002115114BA00D8BE63 /* ASIS3BucketRequest.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B540400D115114BA00D8BE63 /* ASIS3ObjectRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5404004115114BA00D8BE63 /* ASIS3ObjectRequest.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B540400E115114BA00D8BE63 /* ASIS3ServiceRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5404006115114BA00D8BE63 /* ASIS3ServiceRequest.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B55252B411D22E2200F9B170 /* _Reachability.m in Sources */ = {isa = PBXBuildFile; fileRef = B55252B311D22E2200F9B170 /* _Reachability.m */; }; + B55252B511D22E2200F9B170 /* _Reachability.m in Sources */ = {isa = PBXBuildFile; fileRef = B55252B311D22E2200F9B170 /* _Reachability.m */; }; + B55252B611D22E2200F9B170 /* _Reachability.m in Sources */ = {isa = PBXBuildFile; fileRef = B55252B311D22E2200F9B170 /* _Reachability.m */; }; B558B5EB11C7F9C8009B4627 /* iPadMainWindow.xib in Resources */ = {isa = PBXBuildFile; fileRef = B576D76311C7F4D40059B815 /* iPadMainWindow.xib */; }; B55B604D0F765A320064029C /* ASIFormDataRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60460F765A320064029C /* ASIFormDataRequest.m */; }; B55B604E0F765A320064029C /* ASIHTTPRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60480F765A320064029C /* ASIHTTPRequest.m */; }; B55B604F0F765A320064029C /* ASINetworkQueue.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B604A0F765A320064029C /* ASINetworkQueue.m */; }; - B55B60620F765A750064029C /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60600F765A750064029C /* main.m */; }; - B55B606F0F765A930064029C /* QueueViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60670F765A930064029C /* QueueViewController.m */; }; - B55B60700F765A930064029C /* SynchronousViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B606A0F765A930064029C /* SynchronousViewController.m */; }; - B55B60710F765A930064029C /* iPhoneSampleAppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B606B0F765A930064029C /* iPhoneSampleAppDelegate.m */; }; - B55B60720F765A930064029C /* UploadViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B606C0F765A930064029C /* UploadViewController.m */; }; + B55B60620F765A750064029C /* main.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60600F765A750064029C /* main.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B55B606F0F765A930064029C /* QueueViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60670F765A930064029C /* QueueViewController.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B55B60700F765A930064029C /* SynchronousViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B606A0F765A930064029C /* SynchronousViewController.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B55B60710F765A930064029C /* iPhoneSampleAppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B606B0F765A930064029C /* iPhoneSampleAppDelegate.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B55B60720F765A930064029C /* UploadViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B606C0F765A930064029C /* UploadViewController.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B55B60740F765A990064029C /* iphone-icon.png in Resources */ = {isa = PBXBuildFile; fileRef = B55B60730F765A990064029C /* iphone-icon.png */; }; B55B60CF0F765BBA0064029C /* ASIFormDataRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60460F765A320064029C /* ASIFormDataRequest.m */; }; B55B60D00F765BBD0064029C /* ASIHTTPRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60480F765A320064029C /* ASIHTTPRequest.m */; }; B55B60D10F765BC00064029C /* ASINetworkQueue.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B604A0F765A320064029C /* ASINetworkQueue.m */; }; - B55B60D30F765BC90064029C /* ASIFormDataRequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60530F765A3C0064029C /* ASIFormDataRequestTests.m */; }; - B55B60D40F765BCD0064029C /* ASIHTTPRequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60550F765A3C0064029C /* ASIHTTPRequestTests.m */; }; - B55B60D50F765BD00064029C /* ASINetworkQueueTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60570F765A3C0064029C /* ASINetworkQueueTests.m */; }; - B5652920101C8BD7000499CF /* ASITestCase.m in Sources */ = {isa = PBXBuildFile; fileRef = B565291F101C8BD7000499CF /* ASITestCase.m */; }; + B55B60D30F765BC90064029C /* ASIFormDataRequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60530F765A3C0064029C /* ASIFormDataRequestTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B55B60D40F765BCD0064029C /* ASIHTTPRequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60550F765A3C0064029C /* ASIHTTPRequestTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B55B60D50F765BD00064029C /* ASINetworkQueueTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60570F765A3C0064029C /* ASINetworkQueueTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5652920101C8BD7000499CF /* ASITestCase.m in Sources */ = {isa = PBXBuildFile; fileRef = B565291F101C8BD7000499CF /* ASITestCase.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B56529A3101C8EDA000499CF /* iphone-tests-icon.png in Resources */ = {isa = PBXBuildFile; fileRef = B56529A2101C8EDA000499CF /* iphone-tests-icon.png */; }; B576D4C111C7CC970059B815 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B576D4C011C7CC970059B815 /* CFNetwork.framework */; }; B576D4C411C7CC9C0059B815 /* UIKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B576D4C311C7CC9C0059B815 /* UIKit.framework */; }; @@ -74,42 +74,52 @@ B576D71611C7F34D0059B815 /* ASIAuthenticationDialog.m in Sources */ = {isa = PBXBuildFile; fileRef = B59A87C1103EC6F200300252 /* ASIAuthenticationDialog.m */; }; B576D71D11C7F34D0059B815 /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B576D52C11C7CEFA0059B815 /* Foundation.framework */; }; B576D76611C7F4D90059B815 /* iPhoneMainWindow.xib in Resources */ = {isa = PBXBuildFile; fileRef = B576D76511C7F4D90059B815 /* iPhoneMainWindow.xib */; }; - B57AF5921258B3F1002A1F0C /* WebPageViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B57AF5911258B3F1002A1F0C /* WebPageViewController.m */; }; + B57AF5921258B3F1002A1F0C /* WebPageViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B57AF5911258B3F1002A1F0C /* WebPageViewController.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B57AF5931258B3F1002A1F0C /* WebPageViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B57AF5911258B3F1002A1F0C /* WebPageViewController.m */; }; - B57AF5961258B401002A1F0C /* RequestProgressCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B57AF5951258B401002A1F0C /* RequestProgressCell.m */; }; + B57AF5961258B401002A1F0C /* RequestProgressCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B57AF5951258B401002A1F0C /* RequestProgressCell.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B57AF5971258B401002A1F0C /* RequestProgressCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B57AF5951258B401002A1F0C /* RequestProgressCell.m */; }; B57D0F4812AA7D3600E5F992 /* ASIWebPageRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B57D0F4712AA7D3600E5F992 /* ASIWebPageRequest.m */; }; B57D0F4912AA7D3600E5F992 /* ASIWebPageRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B57D0F4712AA7D3600E5F992 /* ASIWebPageRequest.m */; }; B57D0F4A12AA7D3600E5F992 /* ASIWebPageRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B57D0F4712AA7D3600E5F992 /* ASIWebPageRequest.m */; }; B581DDCA12FDFEEE003BA9D0 /* GHUnitIOS.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B581DDC912FDFEEE003BA9D0 /* GHUnitIOS.framework */; }; - B5873FD610FF28CA001E145F /* ASIS3BucketObject.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FC210FF28CA001E145F /* ASIS3BucketObject.m */; }; - B5873FD810FF28CA001E145F /* ASIS3Request.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FC610FF28CA001E145F /* ASIS3Request.m */; }; - B5873FD910FF28CA001E145F /* ASICloudFilesCDNRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FC910FF28CA001E145F /* ASICloudFilesCDNRequest.m */; }; - B5873FDA10FF28CA001E145F /* ASICloudFilesContainer.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FCB10FF28CA001E145F /* ASICloudFilesContainer.m */; }; - B5873FDB10FF28CA001E145F /* ASICloudFilesContainerRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FCD10FF28CA001E145F /* ASICloudFilesContainerRequest.m */; }; - B5873FDC10FF28CA001E145F /* ASICloudFilesContainerXMLParserDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FCF10FF28CA001E145F /* ASICloudFilesContainerXMLParserDelegate.m */; }; - B5873FDD10FF28CA001E145F /* ASICloudFilesObject.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FD110FF28CA001E145F /* ASICloudFilesObject.m */; }; - B5873FDE10FF28CA001E145F /* ASICloudFilesObjectRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FD310FF28CA001E145F /* ASICloudFilesObjectRequest.m */; }; - B5873FDF10FF28CA001E145F /* ASICloudFilesRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FD510FF28CA001E145F /* ASICloudFilesRequest.m */; }; - B5873FF510FF2904001E145F /* ASICloudFilesRequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FF310FF2904001E145F /* ASICloudFilesRequestTests.m */; }; + B5873FD610FF28CA001E145F /* ASIS3BucketObject.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FC210FF28CA001E145F /* ASIS3BucketObject.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FD810FF28CA001E145F /* ASIS3Request.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FC610FF28CA001E145F /* ASIS3Request.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FD910FF28CA001E145F /* ASICloudFilesCDNRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FC910FF28CA001E145F /* ASICloudFilesCDNRequest.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FDA10FF28CA001E145F /* ASICloudFilesContainer.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FCB10FF28CA001E145F /* ASICloudFilesContainer.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FDB10FF28CA001E145F /* ASICloudFilesContainerRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FCD10FF28CA001E145F /* ASICloudFilesContainerRequest.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FDC10FF28CA001E145F /* ASICloudFilesContainerXMLParserDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FCF10FF28CA001E145F /* ASICloudFilesContainerXMLParserDelegate.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FDD10FF28CA001E145F /* ASICloudFilesObject.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FD110FF28CA001E145F /* ASICloudFilesObject.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FDE10FF28CA001E145F /* ASICloudFilesObjectRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FD310FF28CA001E145F /* ASICloudFilesObjectRequest.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FDF10FF28CA001E145F /* ASICloudFilesRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FD510FF28CA001E145F /* ASICloudFilesRequest.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5873FF510FF2904001E145F /* ASICloudFilesRequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5873FF310FF2904001E145F /* ASICloudFilesRequestTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B59A87C2103EC6F200300252 /* ASIAuthenticationDialog.m in Sources */ = {isa = PBXBuildFile; fileRef = B59A87C1103EC6F200300252 /* ASIAuthenticationDialog.m */; }; B59A87C3103EC6F200300252 /* ASIAuthenticationDialog.m in Sources */ = {isa = PBXBuildFile; fileRef = B59A87C1103EC6F200300252 /* ASIAuthenticationDialog.m */; }; B5BD2AFA11CA541100D7C426 /* iPadSampleAppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2AF911CA541100D7C426 /* iPadSampleAppDelegate.m */; }; B5BD2B0111CA542000D7C426 /* DetailCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2AFC11CA542000D7C426 /* DetailCell.m */; }; B5BD2B0211CA542000D7C426 /* InfoCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2AFE11CA542000D7C426 /* InfoCell.m */; }; B5BD2B0311CA542000D7C426 /* ToggleCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2B0011CA542000D7C426 /* ToggleCell.m */; }; - B5BD2B0411CA542000D7C426 /* DetailCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2AFC11CA542000D7C426 /* DetailCell.m */; }; - B5BD2B0511CA542000D7C426 /* InfoCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2AFE11CA542000D7C426 /* InfoCell.m */; }; - B5BD2B0611CA542000D7C426 /* ToggleCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2B0011CA542000D7C426 /* ToggleCell.m */; }; + B5BD2B0411CA542000D7C426 /* DetailCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2AFC11CA542000D7C426 /* DetailCell.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5BD2B0511CA542000D7C426 /* InfoCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2AFE11CA542000D7C426 /* InfoCell.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5BD2B0611CA542000D7C426 /* ToggleCell.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2B0011CA542000D7C426 /* ToggleCell.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B5BD2B0B11CA542700D7C426 /* RootViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2B0811CA542700D7C426 /* RootViewController.m */; }; B5BD2B0C11CA542700D7C426 /* SampleViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2B0A11CA542700D7C426 /* SampleViewController.m */; }; - B5BD2B0E11CA542700D7C426 /* SampleViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2B0A11CA542700D7C426 /* SampleViewController.m */; }; - B5BF64EF12FDFC7100CBC324 /* GHUnitIOSTestMain.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BF64EE12FDFC7100CBC324 /* GHUnitIOSTestMain.m */; }; - B5C6663E100A82D7004F3C96 /* ASIS3RequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5C6663D100A82D7004F3C96 /* ASIS3RequestTests.m */; }; - B5EA45AA109B56D800E920CB /* StressTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5EA45A9109B56D800E920CB /* StressTests.m */; }; + B5BD2B0E11CA542700D7C426 /* SampleViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BD2B0A11CA542700D7C426 /* SampleViewController.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5BF64EF12FDFC7100CBC324 /* GHUnitIOSTestMain.m in Sources */ = {isa = PBXBuildFile; fileRef = B5BF64EE12FDFC7100CBC324 /* GHUnitIOSTestMain.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5C6663E100A82D7004F3C96 /* ASIS3RequestTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5C6663D100A82D7004F3C96 /* ASIS3RequestTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; + B5EA45AA109B56D800E920CB /* StressTests.m in Sources */ = {isa = PBXBuildFile; fileRef = B5EA45A9109B56D800E920CB /* StressTests.m */; settings = {COMPILER_FLAGS = "-fno-objc-arc"; }; }; B5FE752711DBBA6400F898C8 /* ASIDownloadCache.m in Sources */ = {isa = PBXBuildFile; fileRef = B5FE752511DBBA6400F898C8 /* ASIDownloadCache.m */; }; B5FE752811DBBA6400F898C8 /* ASIDownloadCache.m in Sources */ = {isa = PBXBuildFile; fileRef = B5FE752511DBBA6400F898C8 /* ASIDownloadCache.m */; }; B5FE752911DBBA6400F898C8 /* ASIDownloadCache.m in Sources */ = {isa = PBXBuildFile; fileRef = B5FE752511DBBA6400F898C8 /* ASIDownloadCache.m */; }; + C01EEDD715A2D6DA00052A5F /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B576D52C11C7CEFA0059B815 /* Foundation.framework */; }; + C01EEDF515A2DB6100052A5F /* ASIAuthenticationDialog.m in Sources */ = {isa = PBXBuildFile; fileRef = B59A87C1103EC6F200300252 /* ASIAuthenticationDialog.m */; }; + C01EEDF615A2DB6100052A5F /* ASIInputStream.m in Sources */ = {isa = PBXBuildFile; fileRef = B522DACD1030B2AB009A2D22 /* ASIInputStream.m */; }; + C01EEDF715A2DB6100052A5F /* ASIFormDataRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60460F765A320064029C /* ASIFormDataRequest.m */; }; + C01EEDF815A2DB6100052A5F /* ASIHTTPRequest.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B60480F765A320064029C /* ASIHTTPRequest.m */; }; + C01EEDF915A2DB6100052A5F /* ASINetworkQueue.m in Sources */ = {isa = PBXBuildFile; fileRef = B55B604A0F765A320064029C /* ASINetworkQueue.m */; }; + C01EEDFA15A2DB6100052A5F /* ASIDownloadCache.m in Sources */ = {isa = PBXBuildFile; fileRef = B5FE752511DBBA6400F898C8 /* ASIDownloadCache.m */; }; + C01EEDFB15A2DB6100052A5F /* ASIDataDecompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E6D911257B45800C1E79A /* ASIDataDecompressor.m */; }; + C01EEDFC15A2DB6100052A5F /* ASIDataCompressor.m in Sources */ = {isa = PBXBuildFile; fileRef = B53E6D931257B45800C1E79A /* ASIDataCompressor.m */; }; + C01EEE3415A2DC2300052A5F /* _Reachability.m in Sources */ = {isa = PBXBuildFile; fileRef = B55252B311D22E2200F9B170 /* _Reachability.m */; }; DADCEB8512D5039F00958557 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B576D4C011C7CC970059B815 /* CFNetwork.framework */; }; DADCEB8612D503AD00958557 /* CFNetwork.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B576D4C011C7CC970059B815 /* CFNetwork.framework */; }; DADCEB8A12D503F500958557 /* CoreGraphics.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B576D4D011C7CCBC0059B815 /* CoreGraphics.framework */; }; @@ -127,6 +137,10 @@ DADCEB9F12D505AB00958557 /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = DADCEB9E12D505AB00958557 /* libz.dylib */; }; DADCEBA012D505B900958557 /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = DADCEB9E12D505AB00958557 /* libz.dylib */; }; DADCEBA112D505C700958557 /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = DADCEB9E12D505AB00958557 /* libz.dylib */; }; + F87E05BC193F4446007ACCBC /* ASIHTTPLocalizable.strings in Resources */ = {isa = PBXBuildFile; fileRef = F87E05BF193F4446007ACCBC /* ASIHTTPLocalizable.strings */; }; + F87E05BD193F4446007ACCBC /* ASIHTTPLocalizable.strings in Resources */ = {isa = PBXBuildFile; fileRef = F87E05BF193F4446007ACCBC /* ASIHTTPLocalizable.strings */; }; + F87E05E4193F4AD0007ACCBC /* ASIHTTPLocalizable.strings in Resources */ = {isa = PBXBuildFile; fileRef = F87E05BF193F4446007ACCBC /* ASIHTTPLocalizable.strings */; }; + F87E05F6193F5499007ACCBC /* iphone-tests-icon.png in Resources */ = {isa = PBXBuildFile; fileRef = B56529A2101C8EDA000499CF /* iphone-tests-icon.png */; }; /* End PBXBuildFile section */ /* Begin PBXCopyFilesBuildPhase section */ @@ -175,8 +189,8 @@ B5404005115114BA00D8BE63 /* ASIS3ServiceRequest.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ASIS3ServiceRequest.h; sourceTree = ""; }; B5404006115114BA00D8BE63 /* ASIS3ServiceRequest.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = ASIS3ServiceRequest.m; sourceTree = ""; }; B551DB4610D6938500EC1CBF /* ASIHTTPRequestConfig.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ASIHTTPRequestConfig.h; sourceTree = ""; }; - B55252B211D22E2200F9B170 /* Reachability.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Reachability.h; sourceTree = ""; }; - B55252B311D22E2200F9B170 /* Reachability.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = Reachability.m; sourceTree = ""; }; + B55252B211D22E2200F9B170 /* _Reachability.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.objj.h; path = _Reachability.h; sourceTree = ""; }; + B55252B311D22E2200F9B170 /* _Reachability.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = _Reachability.m; sourceTree = ""; }; B558B58911C7F637009B4627 /* iPhoneInfo.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; name = iPhoneInfo.plist; path = "iPhone Sample/iPhoneInfo.plist"; sourceTree = ""; }; B558B58B11C7F63E009B4627 /* iPadInfo.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; name = iPadInfo.plist; path = "iPhone Sample/iPadInfo.plist"; sourceTree = ""; }; B55B60450F765A320064029C /* ASIFormDataRequest.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ASIFormDataRequest.h; sourceTree = ""; }; @@ -267,8 +281,20 @@ B5FE752511DBBA6400F898C8 /* ASIDownloadCache.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = ASIDownloadCache.m; sourceTree = ""; }; B5FE752611DBBA6400F898C8 /* ASIDownloadCache.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ASIDownloadCache.h; sourceTree = ""; }; B5FE752A11DBBA6A00F898C8 /* ASICacheDelegate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ASICacheDelegate.h; sourceTree = ""; }; + C01EEDD615A2D6DA00052A5F /* libASIHTTPRequestIOS.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = libASIHTTPRequestIOS.a; sourceTree = BUILT_PRODUCTS_DIR; }; + C01EEDDA15A2D6DB00052A5F /* ASIHTTPRequestIOS-Prefix.pch */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "ASIHTTPRequestIOS-Prefix.pch"; sourceTree = ""; }; DADCEB9812D5057700958557 /* libxml2.dylib */ = {isa = PBXFileReference; lastKnownFileType = "compiled.mach-o.dylib"; name = libxml2.dylib; path = /usr/lib/libxml2.dylib; sourceTree = ""; }; DADCEB9E12D505AB00958557 /* libz.dylib */ = {isa = PBXFileReference; lastKnownFileType = "compiled.mach-o.dylib"; name = libz.dylib; path = /usr/lib/libz.dylib; sourceTree = ""; }; + F87E05BE193F4446007ACCBC /* de */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = de; path = de.lproj/ASIHTTPLocalizable.strings; sourceTree = ""; }; + F87E05C0193F4451007ACCBC /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/ASIHTTPLocalizable.strings; sourceTree = ""; }; + F87E05D7193F4AB1007ACCBC /* ASIHTTPResourceBundle.bundle */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = ASIHTTPResourceBundle.bundle; sourceTree = BUILT_PRODUCTS_DIR; }; + F87E05D8193F4AB1007ACCBC /* CoreFoundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreFoundation.framework; path = System/Library/Frameworks/CoreFoundation.framework; sourceTree = SDKROOT; }; + F87E05DC193F4AB1007ACCBC /* ASIHTTPResourceBundle-Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = "ASIHTTPResourceBundle-Info.plist"; sourceTree = ""; }; + F87E05DE193F4AB1007ACCBC /* en */ = {isa = PBXFileReference; lastKnownFileType = text.plist.strings; name = en; path = en.lproj/InfoPlist.strings; sourceTree = ""; }; + F87E05E0193F4AB1007ACCBC /* ASIHTTPResourceBundle-Prefix.pch */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "ASIHTTPResourceBundle-Prefix.pch"; sourceTree = ""; }; + F8D2676D174CDFC000F1D9E0 /* asihttp-Prefix.pch */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "asihttp-Prefix.pch"; sourceTree = ""; }; + F8D2676E174CDFC000F1D9E0 /* asihttp.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.objj.h; path = asihttp.h; sourceTree = ""; }; + F8D26770174CDFC000F1D9E0 /* asihttp.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = asihttp.m; sourceTree = ""; }; /* End PBXFileReference section */ /* Begin PBXFrameworksBuildPhase section */ @@ -319,6 +345,21 @@ ); runOnlyForDeploymentPostprocessing = 0; }; + C01EEDD315A2D6DA00052A5F /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + C01EEDD715A2D6DA00052A5F /* Foundation.framework in Frameworks */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + F87E05D4193F4AB1007ACCBC /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; /* End PBXFrameworksBuildPhase section */ /* Begin PBXGroup section */ @@ -359,6 +400,8 @@ 1D6058910D05DD3D006BFB54 /* ASIHTTPRequest iPhone.app */, B55B60C70F765BB00064029C /* Tests.app */, B576D72311C7F34D0059B815 /* ASIHTTPRequest iPad.app */, + C01EEDD615A2D6DA00052A5F /* libASIHTTPRequestIOS.a */, + F87E05D7193F4AB1007ACCBC /* ASIHTTPResourceBundle.bundle */, ); name = Products; sourceTree = ""; @@ -370,6 +413,9 @@ 080E96DDFE201D6D7F000001 /* Classes */, 29B97315FDCFA39411CA2CEA /* Other Sources */, 29B97317FDCFA39411CA2CEA /* Resources */, + F8D2676B174CDFC000F1D9E0 /* asihttp */, + C01EEDD815A2D6DB00052A5F /* ASIHTTPRequest-iOS */, + F87E05DA193F4AB1007ACCBC /* ASIHTTPResourceBundle */, 29B97323FDCFA39411CA2CEA /* Frameworks */, 19C28FACFE9D520D11CA2CBB /* Products */, ); @@ -415,6 +461,7 @@ B56529A2101C8EDA000499CF /* iphone-tests-icon.png */, B55B60730F765A990064029C /* iphone-icon.png */, B55B60CB0F765BB10064029C /* Tests-Info.plist */, + F87E05BF193F4446007ACCBC /* ASIHTTPLocalizable.strings */, ); name = Resources; sourceTree = ""; @@ -432,6 +479,7 @@ B576D4C311C7CC9C0059B815 /* UIKit.framework */, DADCEB9812D5057700958557 /* libxml2.dylib */, DADCEB9E12D505AB00958557 /* libz.dylib */, + F87E05D8193F4AB1007ACCBC /* CoreFoundation.framework */, ); name = Frameworks; sourceTree = ""; @@ -458,8 +506,8 @@ B55252B111D22E2200F9B170 /* Reachability */ = { isa = PBXGroup; children = ( - B55252B211D22E2200F9B170 /* Reachability.h */, - B55252B311D22E2200F9B170 /* Reachability.m */, + B55252B211D22E2200F9B170 /* _Reachability.h */, + B55252B311D22E2200F9B170 /* _Reachability.m */, ); path = Reachability; sourceTree = ""; @@ -552,8 +600,70 @@ path = External; sourceTree = ""; }; + C01EEDD815A2D6DB00052A5F /* ASIHTTPRequest-iOS */ = { + isa = PBXGroup; + children = ( + C01EEDD915A2D6DB00052A5F /* Supporting Files */, + ); + path = "ASIHTTPRequest-iOS"; + sourceTree = ""; + }; + C01EEDD915A2D6DB00052A5F /* Supporting Files */ = { + isa = PBXGroup; + children = ( + C01EEDDA15A2D6DB00052A5F /* ASIHTTPRequestIOS-Prefix.pch */, + ); + name = "Supporting Files"; + sourceTree = ""; + }; + F87E05DA193F4AB1007ACCBC /* ASIHTTPResourceBundle */ = { + isa = PBXGroup; + children = ( + F87E05DB193F4AB1007ACCBC /* Supporting Files */, + ); + path = ASIHTTPResourceBundle; + sourceTree = ""; + }; + F87E05DB193F4AB1007ACCBC /* Supporting Files */ = { + isa = PBXGroup; + children = ( + F87E05DC193F4AB1007ACCBC /* ASIHTTPResourceBundle-Info.plist */, + F87E05DD193F4AB1007ACCBC /* InfoPlist.strings */, + F87E05E0193F4AB1007ACCBC /* ASIHTTPResourceBundle-Prefix.pch */, + ); + name = "Supporting Files"; + sourceTree = ""; + }; + F8D2676B174CDFC000F1D9E0 /* asihttp */ = { + isa = PBXGroup; + children = ( + F8D2676E174CDFC000F1D9E0 /* asihttp.h */, + F8D26770174CDFC000F1D9E0 /* asihttp.m */, + F8D2676C174CDFC000F1D9E0 /* Supporting Files */, + ); + path = asihttp; + sourceTree = ""; + }; + F8D2676C174CDFC000F1D9E0 /* Supporting Files */ = { + isa = PBXGroup; + children = ( + F8D2676D174CDFC000F1D9E0 /* asihttp-Prefix.pch */, + ); + name = "Supporting Files"; + sourceTree = ""; + }; /* End PBXGroup section */ +/* Begin PBXHeadersBuildPhase section */ + C01EEDD415A2D6DA00052A5F /* Headers */ = { + isa = PBXHeadersBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; +/* End PBXHeadersBuildPhase section */ + /* Begin PBXNativeTarget section */ 1D6058900D05DD3D006BFB54 /* iPhone */ = { isa = PBXNativeTarget; @@ -610,6 +720,40 @@ productReference = B576D72311C7F34D0059B815 /* ASIHTTPRequest iPad.app */; productType = "com.apple.product-type.application"; }; + C01EEDD515A2D6DA00052A5F /* ASIHTTPRequestIOS */ = { + isa = PBXNativeTarget; + buildConfigurationList = C01EEDE015A2D6DB00052A5F /* Build configuration list for PBXNativeTarget "ASIHTTPRequestIOS" */; + buildPhases = ( + C01EEDD215A2D6DA00052A5F /* Sources */, + C01EEDD315A2D6DA00052A5F /* Frameworks */, + C01EEDD415A2D6DA00052A5F /* Headers */, + ); + buildRules = ( + ); + dependencies = ( + ); + name = ASIHTTPRequestIOS; + productName = ASIHTTPRequestMobile; + productReference = C01EEDD615A2D6DA00052A5F /* libASIHTTPRequestIOS.a */; + productType = "com.apple.product-type.library.static"; + }; + F87E05D6193F4AB1007ACCBC /* ASIHTTPResourceBundle */ = { + isa = PBXNativeTarget; + buildConfigurationList = F87E05E1193F4AB1007ACCBC /* Build configuration list for PBXNativeTarget "ASIHTTPResourceBundle" */; + buildPhases = ( + F87E05D3193F4AB1007ACCBC /* Sources */, + F87E05D4193F4AB1007ACCBC /* Frameworks */, + F87E05D5193F4AB1007ACCBC /* Resources */, + ); + buildRules = ( + ); + dependencies = ( + ); + name = ASIHTTPResourceBundle; + productName = ASIHTTPResourceBundle; + productReference = F87E05D7193F4AB1007ACCBC /* ASIHTTPResourceBundle.bundle */; + productType = "com.apple.product-type.bundle"; + }; /* End PBXNativeTarget section */ /* Begin PBXProject section */ @@ -627,6 +771,7 @@ Japanese, French, German, + en, ); mainGroup = 29B97314FDCFA39411CA2CEA /* iPhone */; projectDirPath = ""; @@ -635,6 +780,8 @@ 1D6058900D05DD3D006BFB54 /* iPhone */, B55B60C60F765BB00064029C /* Tests */, B576D70211C7F34D0059B815 /* iPad */, + C01EEDD515A2D6DA00052A5F /* ASIHTTPRequestIOS */, + F87E05D6193F4AB1007ACCBC /* ASIHTTPResourceBundle */, ); }; /* End PBXProject section */ @@ -646,6 +793,7 @@ files = ( B55B60740F765A990064029C /* iphone-icon.png in Resources */, B576D76611C7F4D90059B815 /* iPhoneMainWindow.xib in Resources */, + F87E05BC193F4446007ACCBC /* ASIHTTPLocalizable.strings in Resources */, B523254311CA01F1006C6E5A /* Sample.xib in Resources */, B50F661A1297FA45003887B1 /* strict.xcconfig in Resources */, ); @@ -670,6 +818,16 @@ B523254211CA01F1006C6E5A /* Sample.xib in Resources */, B52325AD11CA05A8006C6E5A /* info.png in Resources */, B50F66191297FA45003887B1 /* strict.xcconfig in Resources */, + F87E05BD193F4446007ACCBC /* ASIHTTPLocalizable.strings in Resources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + F87E05D5193F4AB1007ACCBC /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + F87E05F6193F5499007ACCBC /* iphone-tests-icon.png in Resources */, + F87E05E4193F4AD0007ACCBC /* ASIHTTPLocalizable.strings in Resources */, ); runOnlyForDeploymentPostprocessing = 0; }; @@ -737,7 +895,7 @@ B5BD2B0511CA542000D7C426 /* InfoCell.m in Sources */, B5BD2B0611CA542000D7C426 /* ToggleCell.m in Sources */, B5BD2B0E11CA542700D7C426 /* SampleViewController.m in Sources */, - B55252B511D22E2200F9B170 /* Reachability.m in Sources */, + B55252B511D22E2200F9B170 /* _Reachability.m in Sources */, B5FE752811DBBA6400F898C8 /* ASIDownloadCache.m in Sources */, B53E6D971257B45800C1E79A /* ASIDataDecompressor.m in Sources */, B53E6D981257B45800C1E79A /* ASIDataCompressor.m in Sources */, @@ -778,7 +936,7 @@ B540400C115114BA00D8BE63 /* ASIS3BucketRequest.m in Sources */, B540400D115114BA00D8BE63 /* ASIS3ObjectRequest.m in Sources */, B540400E115114BA00D8BE63 /* ASIS3ServiceRequest.m in Sources */, - B55252B411D22E2200F9B170 /* Reachability.m in Sources */, + B55252B411D22E2200F9B170 /* _Reachability.m in Sources */, B5FE752711DBBA6400F898C8 /* ASIDownloadCache.m in Sources */, B51A1A9B11DDF85100ED75CF /* ASIDownloadCacheTests.m in Sources */, B50C1823121C26DB0055FCAB /* ClientCertificateTests.m in Sources */, @@ -811,7 +969,7 @@ B5BD2B0311CA542000D7C426 /* ToggleCell.m in Sources */, B5BD2B0B11CA542700D7C426 /* RootViewController.m in Sources */, B5BD2B0C11CA542700D7C426 /* SampleViewController.m in Sources */, - B55252B611D22E2200F9B170 /* Reachability.m in Sources */, + B55252B611D22E2200F9B170 /* _Reachability.m in Sources */, B5FE752911DBBA6400F898C8 /* ASIDownloadCache.m in Sources */, B53E6D991257B45800C1E79A /* ASIDataDecompressor.m in Sources */, B53E6D9A1257B45800C1E79A /* ASIDataCompressor.m in Sources */, @@ -821,14 +979,59 @@ ); runOnlyForDeploymentPostprocessing = 0; }; + C01EEDD215A2D6DA00052A5F /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + C01EEDF515A2DB6100052A5F /* ASIAuthenticationDialog.m in Sources */, + C01EEDF615A2DB6100052A5F /* ASIInputStream.m in Sources */, + C01EEDF715A2DB6100052A5F /* ASIFormDataRequest.m in Sources */, + C01EEDF815A2DB6100052A5F /* ASIHTTPRequest.m in Sources */, + C01EEDF915A2DB6100052A5F /* ASINetworkQueue.m in Sources */, + C01EEDFA15A2DB6100052A5F /* ASIDownloadCache.m in Sources */, + C01EEDFB15A2DB6100052A5F /* ASIDataDecompressor.m in Sources */, + C01EEDFC15A2DB6100052A5F /* ASIDataCompressor.m in Sources */, + C01EEE3415A2DC2300052A5F /* _Reachability.m in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; + F87E05D3193F4AB1007ACCBC /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; /* End PBXSourcesBuildPhase section */ +/* Begin PBXVariantGroup section */ + F87E05BF193F4446007ACCBC /* ASIHTTPLocalizable.strings */ = { + isa = PBXVariantGroup; + children = ( + F87E05BE193F4446007ACCBC /* de */, + F87E05C0193F4451007ACCBC /* en */, + ); + name = ASIHTTPLocalizable.strings; + sourceTree = ""; + }; + F87E05DD193F4AB1007ACCBC /* InfoPlist.strings */ = { + isa = PBXVariantGroup; + children = ( + F87E05DE193F4AB1007ACCBC /* en */, + ); + name = InfoPlist.strings; + sourceTree = ""; + }; +/* End PBXVariantGroup section */ + /* Begin XCBuildConfiguration section */ 1D6058940D05DD3E006BFB54 /* Debug */ = { isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = NO; - "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; + CLANG_ENABLE_OBJC_ARC = YES; + CODE_SIGN_IDENTITY = ""; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = ""; COPY_PHASE_STRIP = NO; GCC_C_LANGUAGE_STANDARD = "compiler-default"; GCC_DYNAMIC_NO_PIC = NO; @@ -838,9 +1041,11 @@ GCC_VERSION = com.apple.compilers.llvm.clang.1_0; HEADER_SEARCH_PATHS = "${SDK_DIR}/usr/include/libxml2"; INFOPLIST_FILE = "iPhone Sample/iPhoneInfo.plist"; - IPHONEOS_DEPLOYMENT_TARGET = 3.1.3; + IPHONEOS_DEPLOYMENT_TARGET = 6.0; + ONLY_ACTIVE_ARCH = YES; PRODUCT_NAME = "ASIHTTPRequest iPhone"; - "PROVISIONING_PROFILE[sdk=iphoneos*]" = ""; + PROVISIONING_PROFILE = "1EF820DC-2714-4C87-9291-080265963509"; + "PROVISIONING_PROFILE[sdk=iphoneos*]" = "1EF820DC-2714-4C87-9291-080265963509"; TARGETED_DEVICE_FAMILY = 1; }; name = Debug; @@ -849,16 +1054,19 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = NO; - "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; + CLANG_ENABLE_OBJC_ARC = YES; + CODE_SIGN_IDENTITY = ""; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = ""; COPY_PHASE_STRIP = YES; GCC_PRECOMPILE_PREFIX_HEADER = YES; GCC_PREFIX_HEADER = "iPhone Sample/iPhone_Prefix.pch"; GCC_VERSION = com.apple.compilers.llvm.clang.1_0; HEADER_SEARCH_PATHS = "${SDK_DIR}/usr/include/libxml2"; INFOPLIST_FILE = "iPhone Sample/iPhoneInfo.plist"; - IPHONEOS_DEPLOYMENT_TARGET = 3.1.3; + IPHONEOS_DEPLOYMENT_TARGET = 6.0; PRODUCT_NAME = "ASIHTTPRequest iPhone"; - "PROVISIONING_PROFILE[sdk=iphoneos*]" = ""; + PROVISIONING_PROFILE = "1EF820DC-2714-4C87-9291-080265963509"; + "PROVISIONING_PROFILE[sdk=iphoneos*]" = "1EF820DC-2714-4C87-9291-080265963509"; TARGETED_DEVICE_FAMILY = 1; }; name = Release; @@ -868,6 +1076,8 @@ baseConfigurationReference = B50F66181297FA45003887B1 /* strict.xcconfig */; buildSettings = { ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_ENABLE_OBJC_ARC = YES; + CODE_SIGN_IDENTITY = "iPhone Developer"; "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; COPY_PHASE_STRIP = NO; FRAMEWORK_SEARCH_PATHS = ( @@ -880,17 +1090,20 @@ GCC_PRECOMPILE_PREFIX_HEADER = YES; GCC_PREFIX_HEADER = "iPhone Sample/iPhone_Prefix.pch"; GCC_PREPROCESSOR_DEFINITIONS = ""; + GCC_TREAT_WARNINGS_AS_ERRORS = YES; GCC_VERSION = com.apple.compilers.llvm.clang.1_0; HEADER_SEARCH_PATHS = "${SDK_DIR}/usr/include/libxml2"; INFOPLIST_FILE = "iPhone Sample/Tests-Info.plist"; - IPHONEOS_DEPLOYMENT_TARGET = 3.2.2; + IPHONEOS_DEPLOYMENT_TARGET = 6.0; LIBRARY_SEARCH_PATHS = ""; + ONLY_ACTIVE_ARCH = NO; OTHER_LDFLAGS = ( "-ObjC", "-all_load", ); PRODUCT_NAME = Tests; "PROVISIONING_PROFILE[sdk=iphoneos*]" = ""; + VALID_ARCHS = armv7; WARNING_CFLAGS = ""; }; name = Debug; @@ -900,6 +1113,7 @@ baseConfigurationReference = B50F66181297FA45003887B1 /* strict.xcconfig */; buildSettings = { ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_ENABLE_OBJC_ARC = YES; CODE_SIGN_IDENTITY = "iPhone Developer"; COPY_PHASE_STRIP = YES; DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; @@ -911,11 +1125,12 @@ GCC_PRECOMPILE_PREFIX_HEADER = YES; GCC_PREFIX_HEADER = "iPhone Sample/iPhone_Prefix.pch"; GCC_PREPROCESSOR_DEFINITIONS = ""; + GCC_TREAT_WARNINGS_AS_ERRORS = YES; GCC_VERSION = com.apple.compilers.llvm.clang.1_0; HEADER_SEARCH_PATHS = "${SDK_DIR}/usr/include/libxml2"; INFOPLIST_FILE = "iPhone Sample/Tests-Info.plist"; INSTALL_PATH = "$(HOME)/Applications"; - IPHONEOS_DEPLOYMENT_TARGET = 3.2.2; + IPHONEOS_DEPLOYMENT_TARGET = 6.0; LIBRARY_SEARCH_PATHS = ""; OTHER_LDFLAGS = ( "-ObjC", @@ -924,6 +1139,7 @@ PRODUCT_NAME = Tests; PROVISIONING_PROFILE = ""; SKIP_INSTALL = YES; + VALID_ARCHS = armv7; }; name = Release; }; @@ -966,28 +1182,152 @@ }; name = Release; }; + C01EEDDE15A2D6DB00052A5F /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + COPY_PHASE_STRIP = NO; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_DYNAMIC_NO_PIC = NO; + GCC_OPTIMIZATION_LEVEL = 0; + GCC_PRECOMPILE_PREFIX_HEADER = YES; + GCC_PREFIX_HEADER = "ASIHTTPRequest-iOS/ASIHTTPRequestIOS-Prefix.pch"; + GCC_PREPROCESSOR_DEFINITIONS = ( + "DEBUG=1", + "$(inherited)", + ); + GCC_SYMBOLS_PRIVATE_EXTERN = NO; + GCC_VERSION = com.apple.compilers.llvm.clang.1_0; + GCC_WARN_UNINITIALIZED_AUTOS = YES; + IPHONEOS_DEPLOYMENT_TARGET = 5.1; + OTHER_LDFLAGS = "-ObjC"; + PRODUCT_NAME = "$(TARGET_NAME)"; + SKIP_INSTALL = YES; + }; + name = Debug; + }; + C01EEDDF15A2D6DB00052A5F /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + COPY_PHASE_STRIP = YES; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_PRECOMPILE_PREFIX_HEADER = YES; + GCC_PREFIX_HEADER = "ASIHTTPRequest-iOS/ASIHTTPRequestIOS-Prefix.pch"; + GCC_VERSION = com.apple.compilers.llvm.clang.1_0; + GCC_WARN_UNINITIALIZED_AUTOS = YES; + IPHONEOS_DEPLOYMENT_TARGET = 5.1; + OTHER_LDFLAGS = "-ObjC"; + PRODUCT_NAME = "$(TARGET_NAME)"; + SKIP_INSTALL = YES; + VALIDATE_PRODUCT = YES; + }; + name = Release; + }; C01FCF4F08A954540054247B /* Debug */ = { isa = XCBuildConfiguration; buildSettings = { - ARCHS = "$(ARCHS_STANDARD_32_BIT)"; + CLANG_ENABLE_OBJC_ARC = YES; "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; GCC_C_LANGUAGE_STANDARD = c99; GCC_WARN_ABOUT_RETURN_TYPE = YES; GCC_WARN_UNUSED_VARIABLE = YES; - ONLY_ACTIVE_ARCH = YES; + ONLY_ACTIVE_ARCH = NO; SDKROOT = iphoneos; + SKIP_INSTALL = YES; }; name = Debug; }; C01FCF5008A954540054247B /* Release */ = { isa = XCBuildConfiguration; buildSettings = { - ARCHS = "$(ARCHS_STANDARD_32_BIT)"; + CLANG_ENABLE_OBJC_ARC = YES; "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; GCC_C_LANGUAGE_STANDARD = c99; GCC_WARN_ABOUT_RETURN_TYPE = YES; GCC_WARN_UNUSED_VARIABLE = YES; SDKROOT = iphoneos; + SKIP_INSTALL = YES; + }; + name = Release; + }; + F87E05E2193F4AB1007ACCBC /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + COMBINE_HIDPI_IMAGES = YES; + COPY_PHASE_STRIP = NO; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_DYNAMIC_NO_PIC = NO; + GCC_ENABLE_OBJC_EXCEPTIONS = YES; + GCC_OPTIMIZATION_LEVEL = 0; + GCC_PRECOMPILE_PREFIX_HEADER = YES; + GCC_PREFIX_HEADER = "ASIHTTPResourceBundle/ASIHTTPResourceBundle-Prefix.pch"; + GCC_PREPROCESSOR_DEFINITIONS = ( + "DEBUG=1", + "$(inherited)", + ); + GCC_SYMBOLS_PRIVATE_EXTERN = NO; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + INFOPLIST_FILE = "ASIHTTPResourceBundle/ASIHTTPResourceBundle-Info.plist"; + INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Bundles"; + MACOSX_DEPLOYMENT_TARGET = 10.9; + ONLY_ACTIVE_ARCH = YES; + PRODUCT_NAME = "$(TARGET_NAME)"; + SDKROOT = macosx; + WRAPPER_EXTENSION = bundle; + }; + name = Debug; + }; + F87E05E3193F4AB1007ACCBC /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x"; + CLANG_CXX_LIBRARY = "libc++"; + CLANG_ENABLE_MODULES = YES; + CLANG_WARN_BOOL_CONVERSION = YES; + CLANG_WARN_CONSTANT_CONVERSION = YES; + CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; + CLANG_WARN_EMPTY_BODY = YES; + CLANG_WARN_ENUM_CONVERSION = YES; + CLANG_WARN_INT_CONVERSION = YES; + CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; + CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; + COMBINE_HIDPI_IMAGES = YES; + COPY_PHASE_STRIP = YES; + DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; + ENABLE_NS_ASSERTIONS = NO; + GCC_C_LANGUAGE_STANDARD = gnu99; + GCC_ENABLE_OBJC_EXCEPTIONS = YES; + GCC_PRECOMPILE_PREFIX_HEADER = YES; + GCC_PREFIX_HEADER = "ASIHTTPResourceBundle/ASIHTTPResourceBundle-Prefix.pch"; + GCC_WARN_64_TO_32_BIT_CONVERSION = YES; + GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; + GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; + GCC_WARN_UNUSED_FUNCTION = YES; + INFOPLIST_FILE = "ASIHTTPResourceBundle/ASIHTTPResourceBundle-Info.plist"; + INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Bundles"; + MACOSX_DEPLOYMENT_TARGET = 10.9; + PRODUCT_NAME = "$(TARGET_NAME)"; + SDKROOT = macosx; + WRAPPER_EXTENSION = bundle; }; name = Release; }; @@ -1021,6 +1361,15 @@ defaultConfigurationIsVisible = 0; defaultConfigurationName = Release; }; + C01EEDE015A2D6DB00052A5F /* Build configuration list for PBXNativeTarget "ASIHTTPRequestIOS" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + C01EEDDE15A2D6DB00052A5F /* Debug */, + C01EEDDF15A2D6DB00052A5F /* Release */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; C01FCF4E08A954540054247B /* Build configuration list for PBXProject "iPhone" */ = { isa = XCConfigurationList; buildConfigurations = ( @@ -1030,6 +1379,15 @@ defaultConfigurationIsVisible = 0; defaultConfigurationName = Release; }; + F87E05E1193F4AB1007ACCBC /* Build configuration list for PBXNativeTarget "ASIHTTPResourceBundle" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + F87E05E2193F4AB1007ACCBC /* Debug */, + F87E05E3193F4AB1007ACCBC /* Release */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; /* End XCConfigurationList section */ }; rootObject = 29B97313FDCFA39411CA2CEA /* Project object */;