I want to generate a key pair on an iPhone such that the private key can only ever be used to sign blocks of data on that particular iPhone.
The SecKeyGeneratePair
function looks promising. I can generate a key pair to the keychain (using kSecAttrIsPermanent
) and I can disable decryption, derivation and unwrapping with the private key (setting kSecAttrCanDecrypt
, kSecAttrCanDerive
and kSecAttrCanUnwrap
to false
).
Two things worry me about key pairs generated with SecKeyGeneratePair
:
Is it possible to export the private key outside of the keychain into application memory?
Is it possible to change a key property (e.g. set kSecAttrCanDecrypt
to true
) after a private key has been created?
If the option "Yes, export the private key" is greyed out during you export this certificate, it means the private key of this certificate cannot be exported after this certificate is enrolled/requested.
In the details pane, click the certificate that you want to export. On the Action menu, point to All Tasks, and then click Export. In the Certificate Export Wizard, click Yes, export the private key. (This option will appear only if the private key is marked as exportable and you have access to the private key.)
Go to: Certificates > Personal > Certificates. Right-click on the certificate you wish to export and go to All Tasks and hit Export. Hit Next on the Certificate Export Wizard to begin the process. Select “Yes, export the private key” and hit next.
Jailbreak is a tool for exporting certificates marked as non-exportable from the Windows certificate store. This can help when you need to extract certificates for backup or testing. You must have full access to the private key on the filesystem in order for jailbreak to work.
This article provides more details (compared to other answers in this thread):
SecGenerateKeyPair(), which is used to generate RSA and ECDSA key pairs, can now be configured to directly store the generated private key in the device’s Keychain (within the Secure Enclave). This means that the private key can be used without ever leaving the device’s Secure Enclave.
And the important addition:
The kSecAttrTokenIDSecureEnclave
attribute needs to be used when generating the key pair.
If you don't specify this attribute the private key will be accessible even on iOS9.
To answer the first question, the private key cannot be retrieved according to this source:
One API call, SecKeyGeneratePair(), creates a public and private key. The public key is returned to the app, and the private key is sent directly to the Secure Enclave. This private key cannot be retrieved.
More information is available here:
The supported keys are Elliptic Curve P256, the private key is not extractible in any form, even protected, and the applications are RawSign and RawVerify.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With