2011-12-23 102 views
3

我正尝试使用我的应用程序将RSA私钥导入钥匙串。第一次使用SecKeychainImport()导入密钥时,操作成功,随后的导入给我一个EINVAL(100022)错误。将私钥导入钥匙串返回EINVAL错误

如果我退出并在两次导入之间重新启动应用程序,则不会发生这种情况。我包含下面的源代码。

CFArrayRef array = (CFArrayRef)[NSMutableArray array]; 

    SecExternalFormat format = kSecFormatUnknown; 

    //We are always storing a private key… 
    SecExternalItemType type = kSecItemTypePrivateKey; 

    SecKeyImportExportParameters params; 

    SecKeychainRef keychain; 

    SecKeychainCopyDefault(&keychain); 

    memset(&params, 0, sizeof(params)); 

    params.version = SEC_KEY_IMPORT_EXPORT_PARAMS_VERSION; 
    params.flags = kSecKeyNoAccessControl; 
    params.keyUsage = CSSM_KEYUSE_ANY; 
    params.keyAttributes = CSSM_KEYATTR_EXTRACTABLE; 

    err = SecKeychainItemImport((CFDataRef)data, 
             (CFStringRef)@"pem", 
             &format, 
             &type, 
             0, 
             NULL, 
             keychain, 
             &array); 
    if(err == noErr) 
    { 
     //Change the kSecKeyPrintName attribute of the keychain item. 
    } 

    else 
    { 
     //Handle the error by displaying appropriate alert. 
    } 

我缺少什么明显?

+0

不宜第六个参数是'&params'代替的NULL? – 2011-12-24 04:23:20

+0

另外,你在哪个操作系统版本上试过? – 2011-12-24 05:54:57

回答

2

尝试设置params.keyAttribute中的CSSM_KEYATTR_PERMANENT位。在Lion上,如果我明确设置了此属性,我可以将多个PEM装甲的RSA私钥(使用openssl genrsa生成)导入钥匙串。如果我不这样做,导入第一个密钥时我会得到errSecItemNotFound(-25300)。

(不要忘了在生产中部署此代码之前删除kSecKeyNoAccessControl。另外,如果你生成密钥自己,可以考虑使用SecKeyGenerate/SecKeyGenerateSymmetric代替。)