繁体   English   中英

如何枚举OS X应用程序中的所有钥匙串项目?

[英]How can I enumerate all Keychain items in my OS X application?

请帮我解决在OS X中枚举钥匙串项的问题。我读了有关枚举iOS应用程序中所有钥匙串项的主题,但想了解如何编写相同的代码,该代码与Core Foundation函数中的主题一样??? 我试图这样做:

CFDictionaryRef query = CFDictionaryCreate ( kCFAllocatorDefault, NULL, NULL, 0, NULL, NULL);
CFTypeRef *result = NULL;

status = SecItemCopyMatching(query, result );
if (status != errSecSuccess)
{
    GetLastError(status);
}

但是这段代码不起作用! 您能帮助我了解我哪里出错了。 函数“ SecItemCopyMatching”返回错误: 传递给该函数的一个或多个参数无效。 错误代码:-50。

您提供的是空字典,而不是有效的查询。

如果您从正在查看的答案中获取代码,然后将其放入项目中:

NSMutableDictionary *query = [NSMutableDictionary dictionaryWithObjectsAndKeys:
                              (__bridge id)kCFBooleanTrue, (__bridge id)kSecReturnAttributes,
                              (__bridge id)kSecMatchLimitAll, (__bridge id)kSecMatchLimit,
                              nil];

NSArray *secItemClasses = [NSArray arrayWithObjects:
                           (__bridge id)kSecClassGenericPassword,
                           (__bridge id)kSecClassInternetPassword,
                           (__bridge id)kSecClassCertificate,
                           (__bridge id)kSecClassKey,
                           (__bridge id)kSecClassIdentity,
                           nil];

for (id secItemClass in secItemClasses) {
    [query setObject:secItemClass forKey:(__bridge id)kSecClass];

    CFTypeRef result = NULL;
    SecItemCopyMatching((__bridge CFDictionaryRef)query, &result);
    NSLog(@"%@", (__bridge id)result);
    if (result != NULL) CFRelease(result);
}

您将获得更快乐的结果。

编辑以添加CoreFoundation等效项

没有理由不能在MacOS命令行工具中包含Cocoa框架(这是我假设您正在编写的内容)。 命令行工具无法轻松包含的是AppKit UI框架。

无论如何,这是等效的CoreFoundation:

CFMutableDictionaryRef query = CFDictionaryCreateMutable(kCFAllocatorDefault, 0,
                                   &kCFTypeDictionaryKeyCallBacks,
                                   &kCFTypeDictionaryValueCallBacks);


CFDictionarySetValue(query, kSecReturnAttributes, kCFBooleanTrue);
CFDictionarySetValue(query, kSecMatchLimit, kSecMatchLimitAll);

CFTypeRef types[5];

types[0] = kSecClassGenericPassword;
types[1] = kSecClassInternetPassword;
types[2] = kSecClassCertificate;
types[3] = kSecClassKey;
types[4] = kSecClassIdentity;

CFArrayRef secItemClasses = CFArrayCreate(NULL, (void *)types, 5, &kCFTypeArrayCallBacks);
CFIndex i, c = CFArrayGetCount(secItemClasses);

for(i = 0; i<c; i++)
{
    CFTypeRef secItemClass = CFArrayGetValueAtIndex(secItemClasses,i);
    CFDictionarySetValue(query, kSecClass, secItemClass);

    CFTypeRef result = NULL;
    SecItemCopyMatching(query, &result);
    NSLog(@"%@", (__bridge id)result);
    if (result != NULL) CFRelease(result);
}

CFRelease(secItemClasses);
CFRelease(query);

当我将其放入自己的测试应用程序中时,我看到大量的各种钥匙串物品和证书。

OP并没有询问其他钥匙串,但是希望这将对将来的读者有所帮助。

迈克尔的代码是显示钥匙串中存储的“一些”物品的简单方法。 经过反复试验,我发现他的代码不会返回iCloud钥匙串。 要查看iCloud钥匙串,请添加键/值对:

NSMutableDictionary *query = [NSMutableDictionary dictionaryWithObjectsAndKeys:
                              (__bridge id)kCFBooleanTrue, (__bridge id)kSecReturnAttributes,
                              (__bridge id)kSecMatchLimitAll, (__bridge id)kSecMatchLimit,
                              //  added to find keychain items saved in iCloud
                              (__bridge id)kCFBooleanTrue, (__bridge id)kSecAttrSynchronizable,
                              nil];

SecItemCopyMatching()的查询字典很重要,很少理解!

**警告:此产品已在iPhone设备上进行了测试,而不是在Mac上进行了测试。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM