当针对我已转换为使用 ARC 的代码运行 Clang 静态分析器时,它报告此代码块中的 NSNumber 为泄漏:
NSNumber *temporaryNumber = [NSNumber numberWithFloat:0.85];
CFNumberRef compressionQuality = CFBridgingRetain(temporaryNumber);
CFDictionarySetValue(snapshotMetaAndOpts, kCGImageDestinationLossyCompressionQuality, compressionQuality);
CFRelease(compressionQuality);
分析器表明,在所有这些之后,创建并存储到临时编号中的 NSNumber 以 +1 保留计数结束,因此泄漏。我知道我可以很容易地做到
CFDictionarySetValue(snapshotMetaAndOpts, kCGImageDestinationLossyCompressionQuality, (__bridge CFNumberRef)[NSNumber numberWithFloat:0.85]);
但我仍在尝试了解 ARC 中桥接的确切操作,因此我试图弄清楚上述内容。实际的分析器输出如下:
我阅读
CFBridgingRetain()
和 __bridge_retained
的方式是,它们通过将保留计数增加 1 来将 ARC 管理的 NSObject 的所有权转移到 Core Foundation。我用相应的 CFRelease()
来平衡它。我希望 NSNumber 被创建为一个自动释放的对象,因此在 ARC 端完全平衡。同样,如果我使用普通的
__bridge
转换执行以下操作:NSNumber *temporaryNumber = [NSNumber numberWithFloat:0.85];
CFNumberRef compressionQuality = (__bridge CFNumberRef)temporaryNumber;
CFDictionarySetValue(snapshotMetaAndOpts, kCGImageDestinationLossyCompressionQuality, compressionQuality);
CFRelease(compressionQuality);
静态分析器给出了一个干净的健康 list 。
我是否误读了对象是免费桥接的方式,或者这是静态分析器中的错误?
最佳答案
编辑:
这是一个分析器错误。我的机器上有最新版本的独立分析器,没有警告。我使用当前的运输分析器对构建进行了验证,并得到了与您相同的结果。看起来已经很不错了。
您使用的是什么版本的 Xcode?我刚刚测试了以下内容。
int main(int argc, char *argv[])
{
@autoreleasepool
{
CFMutableDictionaryRef dict = CFDictionaryCreateMutable(NULL, 0, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks);
NSNumber *temporaryNumber = [NSNumber numberWithFloat:0.85];
CFNumberRef compressionQuality = CFBridgingRetain(temporaryNumber);
CFDictionarySetValue(dict, CFSTR("Test"), compressionQuality);
CFRelease(compressionQuality);
CFRelease(dict);
}
}
这按预期工作并且不提供分析器警告。这是在 10.7 上的最新 4.2,使用 iOS SDK。
关于objective-c - 为什么静态分析器显示此桥接 NSNumber 在 ARC 下泄漏?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/7958048/