Search code examples
iosobjective-ciphonexcode8afnetworking

AFURLSessionManager when my ViewController was navigated app crashed


I have problem in AFURLSessionManager for Objective-C iOS. I have 2 viewController and use AFURLSessionManager for getData from server.

when user navigate to viewContoller2 that have AFURLSessionManager request and user has very bad network and press back button, AFURLSessionManager want to call delegate, crashed and show EXC_BAD_ACCESS(code=EXC_I386_GPFLT)

Crash image

when i navigate to a viewController, AFURLSessionManager task finish late and viewController was changed by user and AFURLSessionManager try call delegates not exists in MEMORY.

Anyone has any idea fix this problem?

This is request code :

- (void) getData
{
    NSMutableURLRequest *req = [[AFJSONRequestSerializer serializer] requestWithMethod:@"GET" URLString:@"http://----------" parameters:nil error:nil];

    AFURLSessionManager *manager = [[AFURLSessionManager alloc] initWithSessionConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];

    req.timeoutInterval= 15;
    [req setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
    [req setValue:@"application/json" forHTTPHeaderField:@"Accept"];

    self.dataTask = [manager dataTaskWithRequest:req completionHandler:^(NSURLResponse * _Nonnull response, id  _Nullable responseObject, NSError * _Nullable error)
     {

         if (!error)
         {
             NSLog(@"Reply JSON >>>>>> responseObject <<<<<: %@", responseObject);


             if ([responseObject isKindOfClass:[NSDictionary class]])
             {
                 if (self.delegate && [self.delegate respondsToSelector:@selector(success:)]) {
                     [self.delegate success:responseObject];
                 }
                 //                  self.colorView.backgroundColor = [UIColor blueColor];
                 return;
             }
             else
             {
                 NSLog(@"Error No dictionary: %@, %@, %@", error, response, responseObject);
                 {
                     //                      self.colorView.backgroundColor = [UIColor redColor];
                     [self.delegate error:error];
                     return;
                 }

             }
         }
         else
         {
             NSLog(@"Error: %@, %@, %@", error, response, responseObject);
             [self.delegate error:error];
             return;

         }

     }];

    [self.dataTask resume];

    if (self.cancelRequest) {
        [self.dataTask cancel];
    }
}

header file :

@protocol WebServicesDelegate <NSObject>

- (void) success:(NSDictionary *) dic;
- (void) error:(NSError *) error;

@end

@interface WebServices : NSObject

@property (assign,nonatomic) id<WebServicesDelegate> delegate;
@property (nonatomic) BOOL cancelRequest;

-(void) setCancelRequest:(BOOL)cancelRequest;
//+(instancetype) shareInstance;

- (void) getData;

@end

Thanks in advance


Solution

  • Debug what self.delegate is. It is definitely not nil otherwise it wouldn't have crashed.

    It crashed because self.delegate is not an NSObject subclass. It is either a scalar or some garbage value.

    I guess you have used assign instead of weak while declaring delegate and because it is assigned, it is resulting in a dangling pointer.

    EDIT(after question update) Change

    @property (assign,nonatomic) id<WebServicesDelegate> delegate;
    

    to

    @property (weak,nonatomic) id<WebServicesDelegate> delegate;