blob: c10a0148e4e2075553a9b953ea8ba7c699b745c0 [file] [log] [blame]
Shawn Willden6270aca2015-05-26 13:12:24 -06001/*
2 * Copyright 2015 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#include "ec_keymaster0_key.h"
18
19#include <memory>
20
Shawn Willden06298102015-05-25 23:12:48 -060021#include <keymaster/android_keymaster_utils.h>
22#include <keymaster/logger.h>
Shawn Willden6270aca2015-05-26 13:12:24 -060023#include <keymaster/soft_keymaster_context.h>
24
25#include "keymaster0_engine.h"
26#include "openssl_utils.h"
27
28using std::unique_ptr;
29
30namespace keymaster {
31
32EcdsaKeymaster0KeyFactory::EcdsaKeymaster0KeyFactory(const SoftKeymasterContext* context,
33 const Keymaster0Engine* engine)
Shawn Willden2612fb52015-07-27 16:58:30 -060034 : EcKeyFactory(context), engine_(engine) {}
Shawn Willden6270aca2015-05-26 13:12:24 -060035
36keymaster_error_t EcdsaKeymaster0KeyFactory::GenerateKey(const AuthorizationSet& key_description,
37 KeymasterKeyBlob* key_blob,
38 AuthorizationSet* hw_enforced,
Shawn Willden06298102015-05-25 23:12:48 -060039 AuthorizationSet* sw_enforced) const {
Shawn Willden6270aca2015-05-26 13:12:24 -060040 if (!key_blob || !hw_enforced || !sw_enforced)
41 return KM_ERROR_OUTPUT_PARAMETER_NULL;
42
43 if (!engine_ || !engine_->supports_ec())
44 return super::GenerateKey(key_description, key_blob, hw_enforced, sw_enforced);
45
46 uint32_t key_size;
47 if (!key_description.GetTagValue(TAG_KEY_SIZE, &key_size)) {
48 LOG_E("%s", "No key size specified for EC key generation");
49 return KM_ERROR_UNSUPPORTED_KEY_SIZE;
50 }
51
52 KeymasterKeyBlob key_material;
53 if (!engine_->GenerateEcKey(key_size, &key_material))
54 return KM_ERROR_UNKNOWN_ERROR;
55
56 // These tags are hardware-enforced. Putting them in the hw_enforced set here will ensure that
57 // context_->CreateKeyBlob doesn't put them in sw_enforced.
58 hw_enforced->push_back(TAG_ALGORITHM, KM_ALGORITHM_EC);
59 hw_enforced->push_back(TAG_KEY_SIZE, key_size);
Shawn Willden34f09c52015-07-23 23:17:39 +000060 hw_enforced->push_back(TAG_ORIGIN, KM_ORIGIN_UNKNOWN);
Shawn Willden6270aca2015-05-26 13:12:24 -060061
Shawn Willden34f09c52015-07-23 23:17:39 +000062 return context_->CreateKeyBlob(key_description, KM_ORIGIN_UNKNOWN, key_material, key_blob,
Shawn Willden6270aca2015-05-26 13:12:24 -060063 hw_enforced, sw_enforced);
64}
65
66keymaster_error_t EcdsaKeymaster0KeyFactory::ImportKey(
67 const AuthorizationSet& key_description, keymaster_key_format_t input_key_material_format,
68 const KeymasterKeyBlob& input_key_material, KeymasterKeyBlob* output_key_blob,
Shawn Willden06298102015-05-25 23:12:48 -060069 AuthorizationSet* hw_enforced, AuthorizationSet* sw_enforced) const {
Shawn Willden6270aca2015-05-26 13:12:24 -060070 if (!output_key_blob || !hw_enforced || !sw_enforced)
71 return KM_ERROR_OUTPUT_PARAMETER_NULL;
72
73 if (!engine_ || !engine_->supports_ec())
74 return super::ImportKey(key_description, input_key_material_format, input_key_material,
75 output_key_blob, hw_enforced, sw_enforced);
76
77 AuthorizationSet authorizations;
78 uint32_t key_size;
79 keymaster_error_t error = UpdateImportKeyDescription(
80 key_description, input_key_material_format, input_key_material, &authorizations, &key_size);
81 if (error != KM_ERROR_OK)
82 return error;
83
84 KeymasterKeyBlob imported_hw_key;
85 if (!engine_->ImportKey(input_key_material_format, input_key_material, &imported_hw_key))
86 return KM_ERROR_UNKNOWN_ERROR;
87
88 // These tags are hardware-enforced. Putting them in the hw_enforced set here will ensure that
89 // context_->CreateKeyBlob doesn't put them in sw_enforced.
90 hw_enforced->push_back(TAG_ALGORITHM, KM_ALGORITHM_EC);
91 hw_enforced->push_back(TAG_KEY_SIZE, key_size);
Shawn Willden34f09c52015-07-23 23:17:39 +000092 hw_enforced->push_back(TAG_ORIGIN, KM_ORIGIN_UNKNOWN);
Shawn Willden6270aca2015-05-26 13:12:24 -060093
Shawn Willden34f09c52015-07-23 23:17:39 +000094 return context_->CreateKeyBlob(authorizations, KM_ORIGIN_UNKNOWN, imported_hw_key,
Shawn Willden6270aca2015-05-26 13:12:24 -060095 output_key_blob, hw_enforced, sw_enforced);
96}
97
98keymaster_error_t EcdsaKeymaster0KeyFactory::LoadKey(const KeymasterKeyBlob& key_material,
Shawn Willden2612fb52015-07-27 16:58:30 -060099 const AuthorizationSet& additional_params,
Shawn Willden6270aca2015-05-26 13:12:24 -0600100 const AuthorizationSet& hw_enforced,
101 const AuthorizationSet& sw_enforced,
Shawn Willden06298102015-05-25 23:12:48 -0600102 UniquePtr<Key>* key) const {
Shawn Willden6270aca2015-05-26 13:12:24 -0600103 if (!key)
104 return KM_ERROR_OUTPUT_PARAMETER_NULL;
105
106 if (sw_enforced.GetTagCount(TAG_ALGORITHM) == 1)
Shawn Willden2612fb52015-07-27 16:58:30 -0600107 return super::LoadKey(key_material, additional_params, hw_enforced, sw_enforced, key);
Shawn Willden6270aca2015-05-26 13:12:24 -0600108
109 unique_ptr<EC_KEY, EC_Delete> ec_key(engine_->BlobToEcKey(key_material));
110 if (!ec_key)
111 return KM_ERROR_UNKNOWN_ERROR;
112
113 keymaster_error_t error;
Shawn Willden0f906ec2015-06-20 09:16:30 -0600114 key->reset(new (std::nothrow)
115 EcKeymaster0Key(ec_key.release(), hw_enforced, sw_enforced, engine_, &error));
Shawn Willden6270aca2015-05-26 13:12:24 -0600116 if (error != KM_ERROR_OK)
117 return error;
118
119 return KM_ERROR_OK;
120}
121
122EcKeymaster0Key::EcKeymaster0Key(EC_KEY* ec_key, const AuthorizationSet& hw_enforced,
123 const AuthorizationSet& sw_enforced,
124 const Keymaster0Engine* engine, keymaster_error_t* error)
Shawn Willden2612fb52015-07-27 16:58:30 -0600125 : EcKey(ec_key, hw_enforced, sw_enforced, error), engine_(engine) {}
Shawn Willden6270aca2015-05-26 13:12:24 -0600126
127} // namespace keymaster