Macos 导出私钥时SecItemExport失败

Macos 导出私钥时SecItemExport失败,macos,security,osx-lion,core-foundation,Macos,Security,Osx Lion,Core Foundation,我想使用新的10.7Security.frameworkAPI导出专用ECDSA密钥,但操作一直失败,错误代码为-26260: errSecPassphraseRequired = -25260, /* Passphrase is required for import/export. */ 我还希望生成的密钥不要添加到密钥链中,因为它们用于其他机器,我将自己处理存储。下面是不起作用的代码-第一次导出成功,但是导入的相同密钥数据如果没有密码就无法再次导出。我还没有为此密钥设置密码短语

我想使用新的10.7
Security.framework
API导出专用ECDSA密钥,但操作一直失败,错误代码为-26260:

errSecPassphraseRequired     = -25260,  /* Passphrase is required for import/export. */
我还希望生成的密钥不要添加到密钥链中,因为它们用于其他机器,我将自己处理存储。下面是不起作用的代码-第一次导出成功,但是导入的相同密钥数据如果没有密码就无法再次导出。我还没有为此密钥设置密码短语。我尝试过多种导出类型的组合,包括包装的OpenSSL和PEM铠装,但似乎没有什么不同。我已经有了使用OpenSSL实现这一点的工作代码,但是由于Lion中不推荐使用它,我想看看新API可以做什么

// Set up the parameters for 256-bit ECDSA
CFMutableDictionaryRef parameters = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks);
CFDictionarySetValue(parameters, kSecAttrKeyType, kSecAttrKeyTypeECDSA);
CFDictionarySetValue(parameters, kSecAttrKeySizeInBits, CFSTR("256")); // kSecp256r1
CFDictionarySetValue(parameters, kSecAttrIsPermanent, kCFBooleanFalse);

// Issue #1:
// SecKeyGeneratePair() adds the keys to the keychain, which I don't want to do
// The docs say that kSecAttrIsPermanent should change this behavior
SecKeyRef publicKey, privateKey;
OSStatus result = SecKeyGeneratePair((CFDictionaryRef)parameters, &publicKey, &privateKey);

CFRelease(parameters), parameters = nullptr;

if(noErr == result) {
    CFDataRef privateKeyData = nullptr;
    result = SecItemExport(privateKey, kSecFormatUnknown, 0, nullptr, &privateKeyData);
    if(noErr == result) {
        CFShow(privateKeyData);

        uint32_t format = kSecFormatUnknown;
        uint32_t itemType = kSecItemTypePrivateKey;
        CFArrayRef items = nullptr;
        result = SecItemImport(privateKeyData, nullptr, &format, &itemType, 0, nullptr, nullptr, &items);

        CFRelease(privateKeyData), privateKeyData = nullptr;
        CFRelease(privateKey), privateKey = nullptr;

        if(noErr == result) {
            privateKey = (SecKeyRef)CFRetain(CFArrayGetValueAtIndex(items, 0));

            CFRelease(items), items = nullptr;

            // Issue #2:
            // SecItemExport() fails with -25260
            result = SecItemExport(privateKey, kSecFormatUnknown, 0, nullptr, &privateKeyData);
            if(noErr == result) {
                CFShow(privateKeyData);
                CFRelease(privateKeyData), privateKeyData = nullptr;
            }
            else
                printf("SecItemExport error: %d\n", result);
        }
        else
            puts("SecItemImport failed");
    }
    else
        printf("SecItemExport error: %d\n", result);
}
else
    printf("SecKeyGeneratePair error: %d\n", result);
以下是示例运行的输出:

<CFData 0x10061b390 [0x7fff79ed3fa0]>{length = 121, capacity = 256, bytes = 0x307702010104209432679e712a4ac156 ... 219ffed31a54aff1}
SecItemExport error: -25260
{length=121,capacity=256,bytes=0x307702019432679E712A4AC156…219ffed31a54aff1}
SecItemExport错误:-25260

这有什么乐趣吗?此外,仅供参考,OpenSSL仅作为操作系统提供的动态库而被弃用。仍然可以
brew安装openssl
,然后以私有动态库的形式静态链接或发布自己的动态库。我相信它被弃用的原因只是界面在不同版本之间变化太大。我在苹果的开发者论坛上发布了同样的问题,大家一致认为,你可以导出一个私钥而不需要密码是一个错误,自动添加钥匙链也是一个错误。我继续使用OpenSSL,因为它是可用的,如果它在10.9中被删除,我会在一年内担心。-25260是“导入或导出需要密码。”-你在SecItemExport中遗漏了参数