IOS:无法从 CryptoKit SecureEnclave 私钥创建 SecKey 表示(OSStatus 错误 -50 - 从数据创建 EC 私钥失败))
Posted
技术标签:
【中文标题】IOS:无法从 CryptoKit SecureEnclave 私钥创建 SecKey 表示(OSStatus 错误 -50 - 从数据创建 EC 私钥失败))【英文标题】:IOS: Unable to create SecKey representation from CryptoKit SecureEnclave Private Key (OSStatus error -50 - EC private key creation from data failed)) 【发布时间】:2021-08-15 12:42:36 【问题描述】:我正在尝试使用CryptoKit
在SecureEnclave
中创建一个私钥/公钥对,然后将对私钥的引用保存在KeyChain
中以供进一步使用。密钥生成完全正常:
let accessControl = SecAccessControlCreateWithFlags(
kCFAllocatorDefault,
kSecAttrAccessibleWhenUnlockedThisDeviceOnly,
[.privateKeyUsage],
nil
)!
let privateKey = try SecureEnclave.P256.Signing.PrivateKey(accessControl: accessControl)
// Describe the key.
let attributes = [
kSecAttrKeyType: kSecAttrKeyTypeECSECPrimeRandom,
kSecAttrKeyClass: kSecAttrKeyClassPrivate
] as [String: Any]
但是当我尝试将刚刚创建的密钥转换为SecKey
以便稍后将其存储在钥匙串中时:
// Get a SecKey representation.
var error: Unmanaged<CFError>?
guard let secKey = SecKeyCreateWithData(key.dataRepresentation as CFData, attributes as CFDictionary, nil) else
throw error!.takeRetainedValue()
失败并出现错误:
The operation couldn’t be completed. (OSStatus error -50 - EC private key creation from data failed)
另一方面,当我删除 SecureEnclave
元素并使用 x963Representation
时,我能够将私钥转换为 SecKey
对象:
let privateKey = P256.Signing.PrivateKey()
guard let secKey = SecKeyCreateWithData(privateKey.x963Representation as CFData, attributes as CFDictionary, nil) else
throw error!.takeRetainedValue()
关于为什么会发生这种情况或我该如何解决这个问题的任何想法?
【问题讨论】:
【参考方案1】:并非所有密钥都可以(直接)存储到钥匙串as described in the documentation 中。要解决此问题,您可以将原始 Data
作为通用密码存储在钥匙串中。 SecureEnclave
键有点可惜。
此外,Secure Enclave 私钥的.dataRepresentation
不是安全框架能够理解的。 Secure Enclave 密钥不打算被提取(据我所知,根本无法提取)。您提取的 blob 是 相同 enclave 可用于重建私钥的容器。在另一部 iPhone 上使用相同的数据不会重新创建密钥。
我不确定将此 blob 作为文件存储在设备上是否存在安全风险。所以我建议你看看前面提到的文档并使用GenericPasswordConvertible
示例。
【讨论】:
以上是关于IOS:无法从 CryptoKit SecureEnclave 私钥创建 SecKey 表示(OSStatus 错误 -50 - 从数据创建 EC 私钥失败))的主要内容,如果未能解决你的问题,请参考以下文章
无法从 UITextField 获取文本 - Swift - iOS