11.5.6.11. Trust Provisioned keys¶
The trust provisioned SE contains ECC-256 and RSA-2048 keys. These keys are provisioned at specific keyIDs. In order to use these keys, we need to pass a magic number along with the corresponding keyID of the key to the keymaster import_key
API. Only when the import_key
parses the key and finds the magic as a part of the key, it returns the key blob of the trust provisioned key.
11.5.6.11.1. Using TP RSA key¶
To use trust provisioned RSA key, pass the key in the following format:
modulus:
a5:a6:b5:b6:a5:a6:b5:b6:xx:xx:xx:xx:xx:xx:xx:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
publicExponent: 65537 (0x10001)
privateExponent:
A5:23:00:67:02:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
prime1:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
prime2:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
exponent1:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
exponent2:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
coefficient:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
Note here that the key modulus starts with the magic A5:A6:B5:B6:A5:A6:B5:B6
and the privateExponent starts with A5
followed by the 32-bit keyID (here, 0x23006702) of the trust provisioned RSA keypair. When an RSA key with modulus starting with the magic and privateExponent starting with A5
is passed to import_key
, the RSA key stored at the corresponding keyID (0x23006702) is returned. An example of java code to import RSA keypair in this format is:
PrivateKey ImportTPKeyRSA() throws NoSuchAlgorithmException,
InvalidKeySpecException
{
PrivateKey privKey;
KeyFactory KeyFac;
BigInteger Mod, PrivExp, PubExp, PrimeP, PrimeQ, PrimeExpP, PrimeExpQ, CrtCoef;
RSAPrivateCrtKeySpec spec;
try {
KeyFac = KeyFactory.getInstance("RSA");
} catch (NoSuchAlgorithmException e) {
throw e;
}
Random rnd = new Random();
StringBuffer temp = new StringBuffer(112);
for(int i=0 ; i<112 ; i++)
{
int val = rnd.nextInt(16);
temp.append(Integer.toString(val, 16));
}
StringBuffer buf = new StringBuffer(128);
String mag = "a5a6b5b6a5a6b5b6";
buf.append(mag);
buf.append(temp);
String mod = buf.toString();
Mod = new BigInteger(mod, 16);
PrivExp = new BigInteger("A523006702", 16); //KeyID in hex at which Trust provisioned key is stored
PubExp = new BigInteger("65537");
PrimeP = new BigInteger("1");
PrimeQ = new BigInteger("1");
PrimeExpP = new BigInteger("1");
PrimeExpQ = new BigInteger("1");
CrtCoef = new BigInteger("1");
// Create a RSA private key spec using components which have the magic and keyID
spec = new RSAPrivateCrtKeySpec(Mod, PubExp, PrivExp, PrimeP, PrimeQ, PrimeExpP, PrimeExpQ, CrtCoef);
try {
// Generate a dummy keypair using key factory which will be in the desired format to export trust provisioned keypair
privKey = KeyFac.generatePrivate(spec);
} catch (InvalidKeySpecException e) {
throw e;
}
return privKey;
}
void SetTPKeyRSA(String Label) throws NoSuchAlgorithmException, InvalidKeySpecException, KeyStoreException,
CertificateException
{
PrivateKey privKey;
X509Certificate cCert;
// Dummy RSA certificate to create a keystore entry
final String cDummyCert = "-----BEGIN CERTIFICATE-----\nMIIB9zCCAWCgAwIBAgIEITKMnTANBgkqhkiG9w0BAQsFADA3MRgwFgYDVQQDEw9JbnRlcm5hbFVzZU9ubHkxGzAZBgNVBAUTEjAyNDk5OTkwMDAwMDAwMDAwMTAeFw0xNzA4MjUwNzIyMDVaFw0zMjA4MjUwNzIyMDVaMDcxGDAWBgNVBAMTD0ludGVybmFsVXNlT25seTEbMBkGA1UEBRMSMDI0OTk5OTAwMDAwMDAwMDAxMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCE+95LNOSG03eAyk5bRC0KvbJVZIw0Ru2jpQyGX1D1ASnPjD4InQLPg9qIvSz3U7m84PR5WLexq+wyUiraMeWpXBlLn8FVQoKNidMF+DhK7TaGWK2oMHFK/s14cnwE1/5Te5uunM7li2NPphTjbUMrUH7Du+t/EWb0UdHN4mGKKQIDAQABoxAwDjAMBgNVHRMEBTADAQH/MA0GCSqGSIb3DQEBCwUAA4GBAAGmSkfLAVijSRRTAdPhqxk0ifNYDJRAqoJNrxiBN2pvsaUFyo8kde7MhCnNNsHZStf8ZdIztKb6G9Lt8HjYmsI6+fCqHxYjEeFcCVc5Vzg5SpzdtxzYLhEwRYLs0Dzv3rSYPXcN475eFQbH83/0tCuGuc3XcbvXjNhdddoZdvNg\n-----END CERTIFICATE-----";
try
{
privKey = ImportTPKeyRSA();
}
catch (Exception e)
{
throw e;
}
Certificate[] aUseCert;
aUseCert = new X509Certificate[1];
CertificateFactory cCertFac;
InputStream in = new ByteArrayInputStream(cDummyCert.getBytes());
try {
cCertFac = CertificateFactory.getInstance("X.509");
} catch (CertificateException e) {
throw e;
}
aUseCert[0] = (X509Certificate) cCertFac.generateCertificate(in);
try
{
// Store the keypair in keystore with alias=Label and dummy certificate chain = aUseCert
m_cKeyStore.setKeyEntry(Label,(Key) privKey,null ,aUseCert);
}
catch (KeyStoreException e)
{
throw e;
}
return;
}
11.5.6.11.2. Using TP EC key¶
To use trust provisioned EC key, pass the key in the following format:
priv:
a5:a6:b5:b6:a5:a6:b5:b6:c3:02:00:01:xx:xx:xx:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
pub:
xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:....
Note here that the private component of the EC keypair contains the magic A5:A6:B5:B6:A5:A6:B5:B6
followed by the 32-bit keyID (here, 0xC3020001) of the trust provisioned EC keypair. When an EC key with private component starting with the magic is passed to import_key
, the EC keypair stored at the corresponding keyID (0xC3020001) is returned. An example of java code to import EC keypair in this format is:
ECPrivateKey ImportTPKeyECC() throws NoSuchAlgorithmException,
InvalidKeySpecException,
InvalidParameterSpecException,
InvalidAlgorithmParameterException, NoSuchProviderException
{
ECPrivateKey privKey;
KeyFactory KeyFac;
BigInteger PrivS;
ECParameterSpec ECSpec;
ECPrivateKeySpec PrivSpec;
Random rnd = new Random();
StringBuffer temp = new StringBuffer(40);
for(int i=0 ; i<40 ; i++)
{
int val = rnd.nextInt(16);
temp.append(Integer.toString(val, 16));
}
StringBuffer buf = new StringBuffer(64);
String mag = "a5a6b5b6a5a6b5b6";
String keyobject = "c3020001";
buf.append(mag);
buf.append(keyobject);
buf.append(temp);
String magic = buf.toString();
PrivS = new BigInteger(magic, 16);
String cECCCurveName = "secp256r1";
AlgorithmParameters algSpec = AlgorithmParameters.getInstance("EC");
try {
algSpec.init(new ECGenParameterSpec(cECCCurveName));
} catch (InvalidParameterSpecException e1) {
e1.printStackTrace();
}
ECSpec = algSpec.getParameterSpec(ECParameterSpec.class);
// Create PrivateKey spec with parameters for curve secp256r1 and private key containing the magic and the keyID
PrivSpec = new ECPrivateKeySpec(PrivS, ECSpec);
try {
KeyFac = KeyFactory.getInstance("EC");
} catch (NoSuchAlgorithmException e) {
throw e;
}
try {
// Generate a dummy keypair using key factory which will be in the desired format to export trust provisioned keypair
privKey = (ECPrivateKey) KeyFac.generatePrivate(PrivSpec);
} catch (InvalidKeySpecException e) {
throw e;
}
return privKey;
}
void SetTPKeyEC(String Label) throws NoSuchAlgorithmException, InvalidKeySpecException, KeyStoreException,
CertificateException, GeneralSecurityException {
ECPrivateKey privKey;
X509Certificate cCert;
final String cDummyCert = "-----BEGIN CERTIFICATE-----\n" +
"MIIBeTCCASCgAwIBAgIJAKtU6mCCLJeyMAoGCCqGSM49BAMCMBExDzANBgNVBAMMBmRlbW9DQTAeFw0xOTA1MDMxNDQyNDVaFw0yNzAxMDExNDQyNDVaMBExDzANBgNVBAMMBmRlbW9DQTBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABKFlRck++xuGvo9FnFp7Tp0vA+xrZ0oIy2bsuzFrlVCZt7J00B2E+kxMFPCISi/wC3xvYYQv6o7l16kcQxw9CByjYTBfMAwGA1UdEwQFMAMBAf8wTwYDVR0RBEgwRoEmZDpOWFAtQTcxQ0gtRDozNzc4MTM0MjYzNzg2MDcxOTY4OTcyNzmGHE5YUDozNzc4MTM0MjYzNzg2MDcxOTY4OTcyNzkwCgYIKoZIzj0EAwIDRwAwRAIgC9849zJCRndqkGMgHYZqq/63cSGmmwlnw6H8eVaNqUwCIESKl/PAkaVE/u/o5a1v4hJ7jLH06NvdaatTINz0umK/\n-----END CERTIFICATE----- ";
privKey = ImportTPKeyECC();
Certificate[] aUseCert;
aUseCert = new X509Certificate[1];
CertificateFactory cCertFac;
InputStream in = new ByteArrayInputStream(cDummyCert.getBytes());
try {
cCertFac = CertificateFactory.getInstance("X.509");
} catch (CertificateException e) {
throw e;
}
aUseCert[0] = (X509Certificate) cCertFac.generateCertificate(in);
try
{
// Store the keypair in keystore with alias=Label and dummy certificate chain = aUseCert
m_cKeyStore.setKeyEntry(Label,(Key) privKey,null ,aUseCert);
}
catch (KeyStoreException e)
{
throw e;
}
return;
}