Tuesday, 10 September 2013

iOS Crash - Asynchronous UIImageView setImage EXC_BAD_ACCESS

iOS Crash - Asynchronous UIImageView setImage EXC_BAD_ACCESS

I did not experience any crashing in testing, but I've gotten a few crash
reports from iTunesConnect that look like this:
Exception Type: EXC_BAD_ACCESS (SIGSEGV)
Exception Codes: KERN_INVALID_ADDRESS at 0x45d319f8
Crashed Thread: 0
Thread 0 name: Dispatch queue: com.apple.main-thread
Thread 0 Crashed:
0 libobjc.A.dylib 0x3a6595be objc_msgSend + 30
1 UIKit 0x34796e30 -[UIImageView setImage:] + 116
2 My App 0x000c40b2 -[AsyncImageView setImage:]
(AsyncImageView.m:224)
3 My App 0x000c3950 __47-[AsyncImageView
loadImageWithURL:animated:]_block_invoke_2 (AsyncImageView.m:147)
AsyncImageView is a typical UIImageView subclass that loads images
asynchronously from a URL.
Here is the asset loading code with the offending line number indicated:
- (void)loadImageWithURL:(NSURL *)url animated:(BOOL)animated {
if (url == nil) {
[self setImage:nil];
return;
}
self.imageAsset = [[Asset alloc] init];
self.imageAsset.assetURL = url;
AssetRequest *request = [[AssetRequest alloc] init];
request.assetURL = url;
__weak AsyncImageView *weakSelf = self;
self.assetLoader = [AssetLoader AssetLoaderWithRequest:request
completion:^(Asset *asset){
dispatch_async(dispatch_get_main_queue(),
^{
if
(weakSelf.imageAsset.assetURL
== asset.assetURL) {
weakSelf.imageAsset
= asset;
if (animated) {
CATransition
*transition
=
[CATransition
animation];
transition.type
=
kCATransitionFade;
transition.duration
= 0.20;
[weakSelf.layer
addAnimation:transition
forKey:nil];
}
[weakSelf
setImage:weakSelf.imageAsset.assetImage];
//THIS IS LINE
147
[weakSelf
setDisplayLoadingIndicator:NO];
[weakSelf
stopAnimating];
}
});
}
error:^(NSError *err){
if
(weakSelf.failedToLoad)
weakSelf.failedToLoad(url);
}];
[self.assetLoader load];
}
And here is where is sets the image, with the offending line number
indicated:
- (void)setImage:(UIImage *)image {
if (image) {
[super setImage:image]; //THIS IS LINE 224
[self hidePlaceholderView];
if (self.imageLoadedBlock)
self.imageLoadedBlock();
}
else {
[self showPlaceholderView];
}
}
The crash report indicates that the crash occurs when setting the image.
Is there any obvious reason why this might happen? Or any further error
checking I can do (I'm already checking that image isn't null)? And again,
this doesn't happen all the time, only once in a while.

No comments:

Post a Comment