我正在使用SecItemCopyMatching访问iOS密钥链。在我从后台重新启动应用程序后,大约每一百次就会得到一个-34018结果代码。文献资料声明:
为密钥链服务分配的错误空间是不连续的:-25240到-25279,-25290到-25329。键链项服务还可以返回noErr (0)或paramErr (-50)或CSSM结果代码。
因此,-34018似乎是一个'CSSM结果代码‘。我跟踪了建议链接,但找不到结果代码。
-34018结果代码是什么?如何获得更可靠的密钥链访问?
- (NSData *)getKeychainData:(NSString *)key
{
NSDictionary *query = @{
(__bridge id)kSecClass:(__bridge id)kSecClassGenericPassword,
(__bridge id)kSecAttrService:SEC_ATTR_SERVICE,
(__bridge id)kSecAttrAccount:key,
(__bridge id)kSecReturnData:@YES
};
CFDataRef result = nil;
OSStatus status = SecItemCopyMatching((__bridge CFDictionaryRef)query, (CFTypeRef *)&result);
if(status == errSecItemNotFound) {
return nil;
}
if(status == noErr) {
return CFBridgingRelease(result);
} else {
[self logError:[NSString stringWithFormat:@"SecItemCopyMatching status %d", (int)status] :nil];
return nil;
}
}发布于 2015-11-19 18:28:23
我一直在研究同样的错误。
它的要点是苹果为了与密钥链通信而使用的安全服务,在罕见的情况下,当用户的设备内存不足时,它会崩溃,并剥夺了应用程序与密钥链对话的能力,从而导致可怕的-34018。
这并不是只在运行Xcode时才发生的,有些人可能会声称。
这是有关来自苹果开发者论坛的苹果的一名工作人员:问题的最新数据。
更新:我们终于能够在iOS 8.3上复制-34018错误。这是识别根源的第一步,然后提出一个解决方案。 和往常一样,我们不能承诺发布时间框架,但这影响了许多开发人员,我们真的希望解决这个问题。 早些时候,我建议在应用程序中添加一个小延迟:didFinishLaunchingWithOptions和applicationDidBecomeActive:,然后访问密钥链作为解决方法。然而,这似乎并没有真正的帮助。这意味着,除了重新启动应用程序之外,目前还没有其他解决办法。 这个问题似乎与内存压力有关,因此,在处理内存警告方面采取更积极的措施可能会减轻问题。
另一位苹果员工:
来自苹果另一名工作人员的2016年3月22日
好的,这是最新的。这是一个复杂的问题,有多种可能的原因:问题的一些实例是由不正确的应用程序签名引起的。您可以很容易地区分这个情况,因为这个问题是100%可重现的。这个问题的一些例子是由iOS如何支持应用程序开发中的一个错误引起的(r.23,991,853)。调试这一点很复杂,因为操作系统中的另一个bug (第23,770,418条)掩盖了它的效果,这意味着只有当设备面临内存压力时才会出现问题。我们相信这些问题在iOS 9.3中得到了解决。我们怀疑这个问题可能还有更多的原因。因此,如果您在运行iOS 9.3或更高版本的用户设备(Xcode尚未讨论过)上看到此问题,请提交一份有关它的错误报告。尝试将设备系统日志包含在您的bug报告中(我意识到在处理客户设备时,这可能很棘手;一种选择是要求客户安装,让他们可以查看系统日志)。如果你确实有一个错误,请张贴你的错误编号,只是为了记录。我谨代表苹果公司感谢大家为追踪这一相当可怕的问题所做的努力。分享和享受
不幸的是,没有已知的解决办法,这个问题在9.3.2Beta 1 (13F51a)中仍未解决。
发布于 2015-05-01 13:20:46
经过一些研究,我发现了这个:http://opensource.apple.com/source/Security/Security-55471/sec/Security/SecBasePriv.h
所以-34018是errSecMissingEntitlement,评论说
Internal error when a required entitlement isn't present.在运行单元测试时,您是否经历过此错误?如果是这样,这可能会有帮助:https://stackoverflow.com/a/22305193/171933
github上的这个问题说,它似乎只发生在从Xcode:https://github.com/soffes/sskeychain/issues/97进行调试时(也见https://stackoverflow.com/a/28256591/171933)。
希望这些都能帮上忙!
发布于 2015-05-08 03:31:24
此代码适用于我:
static const UInt8 kKeychainItemIdentifier[] = "com.apple.dts.KeychainUI\0";
- (NSData *)getKeychainData:(NSString *)key
{
NSData *keychainItemID = [NSData dataWithBytes:kKeychainItemIdentifier length:strlen((const char *)kKeychainItemIdentifier)];
NSDictionary *query = @{
(__bridge id)kSecClass: (__bridge id)kSecClassGenericPassword,
(__bridge id)kSecAttrService: SEC_ATTR_SERVICE,
(__bridge id)kSecAttrAccount: key,
(__bridge id)kSecReturnData: (__bridge id)kCFBooleanTrue,
(__bridge id)kSecAttrGeneric: keychainItemID
};
CFDataRef result = NULL;
OSStatus status = SecItemCopyMatching((__bridge CFDictionaryRef)query, (CFTypeRef *)&result);
if(status == errSecItemNotFound) {
return nil;
}
if(status == noErr) {
return CFBridgingRelease(result);
} else {
[self logError:[NSString stringWithFormat:@"SecItemCopyMatching status %d", (int)status] :nil];
return nil;
}
}OP代码的主要区别是在查询中添加了一个泛型属性。键链项标识符是来自apple的缺省值。这背后的原因是区分可能的不同的密钥链项目彼此。这是使密钥链项目访问更可靠的一种方法。换句话说,从根本上说,这确保了你可以访问苹果的默认密钥链。
https://stackoverflow.com/questions/29740952
复制相似问题