Block stored on self captures self strongly
ID |
objectivec.correctness.retain_cycle_block |
Severity |
low |
Remediation Complexity |
medium |
Remediation Risk |
low |
Remediation Effort |
medium |
Resource |
Resource Management |
Language |
Objective-C |
Description
This block is stored in a property or instance variable of self and sends a message to self, so the object owns the block and the block owns the object: neither is ever deallocated. Capture a weak reference outside the block - __weak typeof(self) weakSelf = self; - and use weakSelf inside it, taking a strong local reference first if the block needs self to stay alive for the duration of the body.
Rationale
This block is stored in a property or instance variable of self and sends a message to self, so the object owns the block and the block owns the object: neither is ever deallocated. Capture a weak reference outside the block - __weak typeof(self) weakSelf = self; - and use weakSelf inside it, taking a strong local reference first if the block needs self to stay alive for the duration of the body.
The following code illustrates the pattern detected by this rule:
@implementation Downloader
- (void)installHandlers {
// FLAGGED: Block stored on self captures self strongly
self.completionHandler = ^{
[self reload];
};
// FLAGGED: Block stored on self captures self strongly
self.progressHandler = ^(NSInteger done) {
[self updateProgress:done];
};
// FLAGGED: Block stored on self captures self strongly
_finishHandler = ^{
[self teardown];
};
// FLAGGED: Block stored on self captures self strongly
_failureHandler = ^(NSError *error) {
[self reportError:error];
};
}
@end