CFArrayRef内存泄漏

时间:2016-07-17 23:22:24

标签: objective-c cocoa

我正在使用LaunchAtLoginController作为我的一个项目,并且在以下方法中始终存在NSArray泄漏内存。如您所见,我将CFArrayRef投射到NSArray (__bridge NSArray*)。我以为我可以使用__bridge_transfer来解决它,但应用程序崩溃了(EXC_BAD_ACCESS)。是因为方法返回了数组中的一个项吗?

- (LSSharedFileListItemRef) findItemWithURL: (NSURL*) wantedURL inFileList: (LSSharedFileListRef) fileList
{
    if (wantedURL == NULL || fileList == NULL)
    return NULL;

    NSArray *listSnapshot = (__bridge NSArray*)(LSSharedFileListCopySnapshot(fileList, NULL));

    LSSharedFileListItemRef itemToReturn = NULL;
    for (id itemObject in listSnapshot) {
        LSSharedFileListItemRef item = (__bridge LSSharedFileListItemRef) itemObject;
        UInt32 resolutionFlags = kLSSharedFileListNoUserInteraction | kLSSharedFileListDoNotMountVolumes;
        CFURLRef currentItemURL = NULL;
        LSSharedFileListItemResolve(item, resolutionFlags, &currentItemURL, NULL);
        if (currentItemURL && CFEqual(currentItemURL, (__bridge CFTypeRef)(wantedURL)))
        {
            CFRelease(currentItemURL);
            itemToReturn = item;
        } else {
            if (currentItemURL)
            CFRelease(currentItemURL);
            if (item)
                CFRelease(item);
        }
    }
    return itemToReturn;
}

这是调用(LSSharedFileListItemRef) findItemWithURL: (NSURL*) wantedURL inFileList: (LSSharedFileListRef) fileList的两种方法。虽然我设法释放了返回的项目,但我永远无法释放显然会泄漏内存的NSArray。

- (BOOL) willLaunchAtLogin: (NSURL*) itemURL
{
    LSSharedFileListItemRef item = [self findItemWithURL:itemURL inFileList:loginItems];
    BOOL willLaunchAtLogin = !!item;
    if (item)
        CFRelease(item);
    return willLaunchAtLogin;
}

- (void) setLaunchAtLogin: (BOOL) enabled forURL: (NSURL*) itemURL
{
    LSSharedFileListItemRef appItem = [self findItemWithURL:itemURL inFileList:loginItems];
    if (enabled && !appItem) {
        LSSharedFileListItemRef itemRef = LSSharedFileListInsertItemURL(loginItems, kLSSharedFileListItemBeforeFirst,
                                  NULL, NULL, (__bridge CFURLRef)itemURL, NULL, NULL);
        if (itemRef)
            CFRelease(itemRef);
    } else if (!enabled && appItem) {
        LSSharedFileListItemRemove(loginItems, appItem);
    }
    if (appItem)
        CFRelease(appItem);
}

我尝试了一切我能想到的解决方案,但没有成功。我错过了什么?

0 个答案:

没有答案