blob: 09b83c082a080a7286ba7801c8098fd0f5772111 [file] [log] [blame]
Shawn Willden128ffe02014-08-06 12:31:33 -06001/*
2 * Copyright 2014 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
Shawn Willdenb6837e72015-05-16 09:20:59 -060017#include <keymaster/android_keymaster.h>
Shawn Willden567a4a02014-12-31 12:14:46 -070018
Shawn Willden128ffe02014-08-06 12:31:33 -060019#include <assert.h>
20#include <string.h>
21
Shawn Willden4db3fbd2014-08-08 22:13:44 -060022#include <cstddef>
23
Shawn Willden1615f2e2014-08-13 10:37:40 -060024#include <openssl/rand.h>
Shawn Willdenffd790c2014-08-18 21:20:06 -060025#include <openssl/x509.h>
Shawn Willden128ffe02014-08-06 12:31:33 -060026
27#include <UniquePtr.h>
28
Shawn Willdenb6837e72015-05-16 09:20:59 -060029#include <keymaster/android_keymaster_utils.h>
Shawn Willden0cb69422015-05-26 08:31:37 -060030#include <keymaster/keymaster_context.h>
Shawn Willden98d9b922014-08-26 08:14:10 -060031
Shawn Willden3879f862014-08-06 14:40:48 -060032#include "ae.h"
Shawn Willdend67afae2014-08-19 12:36:27 -060033#include "key.h"
Shawn Willden567a4a02014-12-31 12:14:46 -070034#include "openssl_err.h"
Shawn Willdend67afae2014-08-19 12:36:27 -060035#include "operation.h"
Shawn Willden23d4a742015-03-19 15:33:21 -060036#include "operation_table.h"
Shawn Willden128ffe02014-08-06 12:31:33 -060037
38namespace keymaster {
39
Shawn Willden2665e862014-11-24 14:46:21 -070040const uint8_t MAJOR_VER = 1;
41const uint8_t MINOR_VER = 0;
42const uint8_t SUBMINOR_VER = 0;
43
Shawn Willden0cb69422015-05-26 08:31:37 -060044AndroidKeymaster::AndroidKeymaster(KeymasterContext* context, size_t operation_table_size)
45 : context_(context), operation_table_(new OperationTable(operation_table_size)) {
Shawn Willden39b970b2014-08-11 09:11:21 -060046}
Shawn Willdena278f612014-12-23 11:22:21 -070047
Shawn Willdenb6837e72015-05-16 09:20:59 -060048AndroidKeymaster::~AndroidKeymaster() {
Shawn Willden39b970b2014-08-11 09:11:21 -060049}
Shawn Willden128ffe02014-08-06 12:31:33 -060050
Shawn Willden128ffe02014-08-06 12:31:33 -060051struct AE_CTX_Delete {
Shawn Willden802bb292014-08-18 10:46:29 -060052 void operator()(ae_ctx* ctx) const { ae_free(ctx); }
Shawn Willden128ffe02014-08-06 12:31:33 -060053};
54typedef UniquePtr<ae_ctx, AE_CTX_Delete> Unique_ae_ctx;
55
Shawn Willden19fca882015-01-22 16:35:30 -070056// TODO(swillden): Unify support analysis. Right now, we have per-keytype methods that determine if
Shawn Willdenb6837e72015-05-16 09:20:59 -060057// specific modes, padding, etc. are supported for that key type, and AndroidKeymaster also has
Shawn Willden19fca882015-01-22 16:35:30 -070058// methods that return the same information. They'll get out of sync. Best to put the knowledge in
Shawn Willdenb6837e72015-05-16 09:20:59 -060059// the keytypes and provide some mechanism for AndroidKeymaster to query the keytypes for the
Shawn Willden19fca882015-01-22 16:35:30 -070060// information.
Shawn Willden128ffe02014-08-06 12:31:33 -060061
62template <typename T>
Shawn Willden06298102015-05-25 23:12:48 -060063bool check_supported(const KeymasterContext& context, keymaster_algorithm_t algorithm,
64 SupportedResponse<T>* response) {
65 if (context.GetKeyFactory(algorithm) == NULL) {
Shawn Willden128ffe02014-08-06 12:31:33 -060066 response->error = KM_ERROR_UNSUPPORTED_ALGORITHM;
67 return false;
68 }
69 return true;
70}
71
Shawn Willdenb6837e72015-05-16 09:20:59 -060072void AndroidKeymaster::GetVersion(const GetVersionRequest&, GetVersionResponse* rsp) {
Shawn Willden2665e862014-11-24 14:46:21 -070073 if (rsp == NULL)
74 return;
75
76 rsp->major_ver = MAJOR_VER;
77 rsp->minor_ver = MINOR_VER;
78 rsp->subminor_ver = SUBMINOR_VER;
79 rsp->error = KM_ERROR_OK;
80}
81
Shawn Willdenb6837e72015-05-16 09:20:59 -060082void AndroidKeymaster::SupportedAlgorithms(
Shawn Willden3809b932014-12-02 06:59:46 -070083 SupportedResponse<keymaster_algorithm_t>* response) const {
Shawn Willden128ffe02014-08-06 12:31:33 -060084 if (response == NULL)
85 return;
Shawn Willdena278f612014-12-23 11:22:21 -070086
Shawn Willdena278f612014-12-23 11:22:21 -070087 response->error = KM_ERROR_OK;
Shawn Willden128ffe02014-08-06 12:31:33 -060088
Shawn Willden06298102015-05-25 23:12:48 -060089 size_t algorithm_count = 0;
90 const keymaster_algorithm_t* algorithms = context_->GetSupportedAlgorithms(&algorithm_count);
91 if (algorithm_count == 0)
92 return;
93 response->results_length = algorithm_count;
94 response->results = dup_array(algorithms, algorithm_count);
95 if (!response->results)
96 response->error = KM_ERROR_MEMORY_ALLOCATION_FAILED;
Shawn Willden128ffe02014-08-06 12:31:33 -060097}
98
Shawn Willden63ac0432014-12-29 14:07:08 -070099template <typename T>
Shawn Willden06298102015-05-25 23:12:48 -0600100void GetSupported(const KeymasterContext& context, keymaster_algorithm_t algorithm,
101 keymaster_purpose_t purpose,
Shawn Willden63ac0432014-12-29 14:07:08 -0700102 const T* (OperationFactory::*get_supported_method)(size_t* count) const,
103 SupportedResponse<T>* response) {
Shawn Willden06298102015-05-25 23:12:48 -0600104 if (response == NULL || !check_supported(context, algorithm, response))
Shawn Willden63ac0432014-12-29 14:07:08 -0700105 return;
106
Shawn Willden06298102015-05-25 23:12:48 -0600107 const OperationFactory* factory = context.GetOperationFactory(algorithm, purpose);
Shawn Willden63ac0432014-12-29 14:07:08 -0700108 if (!factory) {
109 response->error = KM_ERROR_UNSUPPORTED_PURPOSE;
110 return;
111 }
112
113 size_t count;
114 const T* supported = (factory->*get_supported_method)(&count);
115 response->SetResults(supported, count);
116}
117
Shawn Willdenb6837e72015-05-16 09:20:59 -0600118void AndroidKeymaster::SupportedBlockModes(
Shawn Willden63ac0432014-12-29 14:07:08 -0700119 keymaster_algorithm_t algorithm, keymaster_purpose_t purpose,
120 SupportedResponse<keymaster_block_mode_t>* response) const {
Shawn Willden06298102015-05-25 23:12:48 -0600121 GetSupported(*context_, algorithm, purpose, &OperationFactory::SupportedBlockModes, response);
Shawn Willden63ac0432014-12-29 14:07:08 -0700122}
Shawn Willden3809b932014-12-02 06:59:46 -0700123
Shawn Willdenb6837e72015-05-16 09:20:59 -0600124void AndroidKeymaster::SupportedPaddingModes(
Shawn Willden4200f212014-12-02 07:01:21 -0700125 keymaster_algorithm_t algorithm, keymaster_purpose_t purpose,
Shawn Willden3809b932014-12-02 06:59:46 -0700126 SupportedResponse<keymaster_padding_t>* response) const {
Shawn Willden06298102015-05-25 23:12:48 -0600127 GetSupported(*context_, algorithm, purpose, &OperationFactory::SupportedPaddingModes, response);
Shawn Willden128ffe02014-08-06 12:31:33 -0600128}
129
Shawn Willdenb6837e72015-05-16 09:20:59 -0600130void AndroidKeymaster::SupportedDigests(keymaster_algorithm_t algorithm,
131 keymaster_purpose_t purpose,
132 SupportedResponse<keymaster_digest_t>* response) const {
Shawn Willden06298102015-05-25 23:12:48 -0600133 GetSupported(*context_, algorithm, purpose, &OperationFactory::SupportedDigests, response);
Shawn Willden128ffe02014-08-06 12:31:33 -0600134}
135
Shawn Willdenb6837e72015-05-16 09:20:59 -0600136void AndroidKeymaster::SupportedImportFormats(
Shawn Willden3809b932014-12-02 06:59:46 -0700137 keymaster_algorithm_t algorithm, SupportedResponse<keymaster_key_format_t>* response) const {
Shawn Willden06298102015-05-25 23:12:48 -0600138 if (response == NULL || !check_supported(*context_, algorithm, response))
Shawn Willden128ffe02014-08-06 12:31:33 -0600139 return;
140
Shawn Willdena278f612014-12-23 11:22:21 -0700141 size_t count;
142 const keymaster_key_format_t* formats =
Shawn Willden06298102015-05-25 23:12:48 -0600143 context_->GetKeyFactory(algorithm)->SupportedImportFormats(&count);
Shawn Willdena278f612014-12-23 11:22:21 -0700144 response->SetResults(formats, count);
Shawn Willden128ffe02014-08-06 12:31:33 -0600145}
146
Shawn Willdenb6837e72015-05-16 09:20:59 -0600147void AndroidKeymaster::SupportedExportFormats(
Shawn Willden3809b932014-12-02 06:59:46 -0700148 keymaster_algorithm_t algorithm, SupportedResponse<keymaster_key_format_t>* response) const {
Shawn Willden06298102015-05-25 23:12:48 -0600149 if (response == NULL || !check_supported(*context_, algorithm, response))
Shawn Willden128ffe02014-08-06 12:31:33 -0600150 return;
151
Shawn Willdena278f612014-12-23 11:22:21 -0700152 size_t count;
153 const keymaster_key_format_t* formats =
Shawn Willden06298102015-05-25 23:12:48 -0600154 context_->GetKeyFactory(algorithm)->SupportedExportFormats(&count);
Shawn Willdena278f612014-12-23 11:22:21 -0700155 response->SetResults(formats, count);
Shawn Willden128ffe02014-08-06 12:31:33 -0600156}
157
Shawn Willden0cb69422015-05-26 08:31:37 -0600158keymaster_error_t AndroidKeymaster::AddRngEntropy(const AddEntropyRequest& request) {
159 return context_->AddRngEntropy(request.random_data.peek_read(),
160 request.random_data.available_read());
161}
162
Shawn Willdenb6837e72015-05-16 09:20:59 -0600163void AndroidKeymaster::GenerateKey(const GenerateKeyRequest& request,
164 GenerateKeyResponse* response) {
Shawn Willden128ffe02014-08-06 12:31:33 -0600165 if (response == NULL)
166 return;
Shawn Willden128ffe02014-08-06 12:31:33 -0600167
Shawn Willdena278f612014-12-23 11:22:21 -0700168 keymaster_algorithm_t algorithm;
169 KeyFactory* factory = 0;
170 UniquePtr<Key> key;
171 if (!request.key_description.GetTagValue(TAG_ALGORITHM, &algorithm) ||
Shawn Willden06298102015-05-25 23:12:48 -0600172 !(factory = context_->GetKeyFactory(algorithm)))
Shawn Willdena278f612014-12-23 11:22:21 -0700173 response->error = KM_ERROR_UNSUPPORTED_ALGORITHM;
Shawn Willden0cb69422015-05-26 08:31:37 -0600174 else {
175 KeymasterKeyBlob key_blob;
Shawn Willden2beb6282015-05-20 16:36:24 -0600176 response->enforced.Clear();
177 response->unenforced.Clear();
Shawn Willden0cb69422015-05-26 08:31:37 -0600178 response->error = factory->GenerateKey(request.key_description, &key_blob,
179 &response->enforced, &response->unenforced);
180 if (response->error == KM_ERROR_OK)
181 response->key_blob = key_blob.release();
182 }
Shawn Willden128ffe02014-08-06 12:31:33 -0600183}
184
Shawn Willdenb6837e72015-05-16 09:20:59 -0600185void AndroidKeymaster::GetKeyCharacteristics(const GetKeyCharacteristicsRequest& request,
186 GetKeyCharacteristicsResponse* response) {
Shawn Willden1615f2e2014-08-13 10:37:40 -0600187 if (response == NULL)
188 return;
Shawn Willden76364712014-08-11 17:48:04 -0600189
Shawn Willden0cb69422015-05-26 08:31:37 -0600190 KeymasterKeyBlob key_material;
191 response->error =
192 context_->ParseKeyBlob(KeymasterKeyBlob(request.key_blob), request.additional_params,
193 &key_material, &response->enforced, &response->unenforced);
194 if (response->error != KM_ERROR_OK)
Shawn Willden1615f2e2014-08-13 10:37:40 -0600195 return;
Shawn Willden0cb69422015-05-26 08:31:37 -0600196}
Shawn Willden1615f2e2014-08-13 10:37:40 -0600197
Shawn Willden06298102015-05-25 23:12:48 -0600198static KeyFactory* GetKeyFactory(const KeymasterContext& context,
199 const AuthorizationSet& hw_enforced,
Shawn Willden0cb69422015-05-26 08:31:37 -0600200 const AuthorizationSet& sw_enforced,
201 keymaster_algorithm_t* algorithm, keymaster_error_t* error) {
202 *error = KM_ERROR_UNSUPPORTED_ALGORITHM;
203 if (!hw_enforced.GetTagValue(TAG_ALGORITHM, algorithm) &&
204 !sw_enforced.GetTagValue(TAG_ALGORITHM, algorithm))
205 return nullptr;
Shawn Willden06298102015-05-25 23:12:48 -0600206 KeyFactory* factory = context.GetKeyFactory(*algorithm);
Shawn Willden0cb69422015-05-26 08:31:37 -0600207 if (factory)
208 *error = KM_ERROR_OK;
209 return factory;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600210}
211
Shawn Willdenb6837e72015-05-16 09:20:59 -0600212void AndroidKeymaster::BeginOperation(const BeginOperationRequest& request,
213 BeginOperationResponse* response) {
Shawn Willden1615f2e2014-08-13 10:37:40 -0600214 if (response == NULL)
215 return;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600216 response->op_handle = 0;
217
Shawn Willden0cb69422015-05-26 08:31:37 -0600218 AuthorizationSet hw_enforced;
219 AuthorizationSet sw_enforced;
Shawn Willden06298102015-05-25 23:12:48 -0600220 const KeyFactory* key_factory;
Shawn Willden0cb69422015-05-26 08:31:37 -0600221 UniquePtr<Key> key;
222 response->error = LoadKey(request.key_blob, request.additional_params, &hw_enforced,
Shawn Willden06298102015-05-25 23:12:48 -0600223 &sw_enforced, &key_factory, &key);
Shawn Willden2beb6282015-05-20 16:36:24 -0600224 if (response->error != KM_ERROR_OK)
225 return;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600226
Shawn Willdenedb79942015-05-08 06:46:44 -0600227 // TODO(swillden): Move this check to a general authorization checker.
Shawn Willden0cb69422015-05-26 08:31:37 -0600228 // TODO(swillden): Consider introducing error codes for unauthorized usages.
229 response->error = KM_ERROR_INCOMPATIBLE_PURPOSE;
230 if (!hw_enforced.Contains(TAG_PURPOSE, request.purpose) &&
231 !sw_enforced.Contains(TAG_PURPOSE, request.purpose))
Shawn Willdenedb79942015-05-08 06:46:44 -0600232 return;
Shawn Willdenedb79942015-05-08 06:46:44 -0600233
Shawn Willden0cb69422015-05-26 08:31:37 -0600234 response->error = KM_ERROR_UNSUPPORTED_PURPOSE;
Shawn Willden06298102015-05-25 23:12:48 -0600235 OperationFactory* factory = key_factory->GetOperationFactory(request.purpose);
Shawn Willden0cb69422015-05-26 08:31:37 -0600236 if (!factory)
Shawn Willden63ac0432014-12-29 14:07:08 -0700237 return;
Shawn Willden63ac0432014-12-29 14:07:08 -0700238
Shawn Willden3ed6d062015-04-15 13:39:38 -0600239 UniquePtr<Operation> operation(
240 factory->CreateOperation(*key, request.additional_params, &response->error));
Shawn Willdend67afae2014-08-19 12:36:27 -0600241 if (operation.get() == NULL)
Shawn Willden76364712014-08-11 17:48:04 -0600242 return;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600243
Shawn Willden111edb32015-02-05 22:44:24 -0700244 response->output_params.Clear();
245 response->error = operation->Begin(request.additional_params, &response->output_params);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600246 if (response->error != KM_ERROR_OK)
247 return;
248
Shawn Willden23d4a742015-03-19 15:33:21 -0600249 response->error = operation_table_->Add(operation.release(), &response->op_handle);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600250}
251
Shawn Willdenb6837e72015-05-16 09:20:59 -0600252void AndroidKeymaster::UpdateOperation(const UpdateOperationRequest& request,
253 UpdateOperationResponse* response) {
Shawn Willdend6cd7e32014-12-17 08:01:26 -0700254 if (response == NULL)
255 return;
256
Shawn Willden23d4a742015-03-19 15:33:21 -0600257 response->error = KM_ERROR_INVALID_OPERATION_HANDLE;
258 Operation* operation = operation_table_->Find(request.op_handle);
259 if (operation == NULL)
Shawn Willden1615f2e2014-08-13 10:37:40 -0600260 return;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600261
Shawn Willden23d4a742015-03-19 15:33:21 -0600262 response->error = operation->Update(request.additional_params, request.input, &response->output,
263 &response->input_consumed);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600264 if (response->error != KM_ERROR_OK) {
265 // Any error invalidates the operation.
Shawn Willden23d4a742015-03-19 15:33:21 -0600266 operation_table_->Delete(request.op_handle);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600267 }
268}
269
Shawn Willdenb6837e72015-05-16 09:20:59 -0600270void AndroidKeymaster::FinishOperation(const FinishOperationRequest& request,
271 FinishOperationResponse* response) {
Shawn Willdend6cd7e32014-12-17 08:01:26 -0700272 if (response == NULL)
273 return;
274
Shawn Willden23d4a742015-03-19 15:33:21 -0600275 response->error = KM_ERROR_INVALID_OPERATION_HANDLE;
276 Operation* operation = operation_table_->Find(request.op_handle);
277 if (operation == NULL)
Shawn Willden1615f2e2014-08-13 10:37:40 -0600278 return;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600279
Shawn Willden6bfbff02015-02-06 19:48:24 -0700280 response->error =
Shawn Willden23d4a742015-03-19 15:33:21 -0600281 operation->Finish(request.additional_params, request.signature, &response->output);
282 operation_table_->Delete(request.op_handle);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600283}
284
Shawn Willdenb6837e72015-05-16 09:20:59 -0600285keymaster_error_t AndroidKeymaster::AbortOperation(const keymaster_operation_handle_t op_handle) {
Shawn Willden23d4a742015-03-19 15:33:21 -0600286 Operation* operation = operation_table_->Find(op_handle);
287 if (operation == NULL)
Shawn Willden1615f2e2014-08-13 10:37:40 -0600288 return KM_ERROR_INVALID_OPERATION_HANDLE;
Shawn Willden23d4a742015-03-19 15:33:21 -0600289
290 keymaster_error_t error = operation->Abort();
291 operation_table_->Delete(op_handle);
Shawn Willden7ec74f92014-12-11 13:57:59 -0700292 if (error != KM_ERROR_OK)
293 return error;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600294 return KM_ERROR_OK;
Shawn Willden76364712014-08-11 17:48:04 -0600295}
296
Shawn Willdenb6837e72015-05-16 09:20:59 -0600297void AndroidKeymaster::ExportKey(const ExportKeyRequest& request, ExportKeyResponse* response) {
Shawn Willdenffd790c2014-08-18 21:20:06 -0600298 if (response == NULL)
299 return;
300
Shawn Willden0cb69422015-05-26 08:31:37 -0600301 AuthorizationSet hw_enforced;
302 AuthorizationSet sw_enforced;
303 KeymasterKeyBlob key_material;
304 response->error =
305 context_->ParseKeyBlob(KeymasterKeyBlob(request.key_blob), request.additional_params,
306 &key_material, &hw_enforced, &sw_enforced);
307 if (response->error != KM_ERROR_OK)
308 return;
309
Shawn Willden63ac0432014-12-29 14:07:08 -0700310 keymaster_algorithm_t algorithm;
Shawn Willden06298102015-05-25 23:12:48 -0600311 KeyFactory* key_factory =
312 GetKeyFactory(*context_, hw_enforced, sw_enforced, &algorithm, &response->error);
Shawn Willden0cb69422015-05-26 08:31:37 -0600313 if (!key_factory)
314 return;
315
316 UniquePtr<Key> key;
317 response->error = key_factory->LoadKey(key_material, hw_enforced, sw_enforced, &key);
318 if (response->error != KM_ERROR_OK)
Shawn Willdenffd790c2014-08-18 21:20:06 -0600319 return;
320
Shawn Willdenf268d742014-08-19 15:36:26 -0600321 UniquePtr<uint8_t[]> out_key;
322 size_t size;
Shawn Willden0cb69422015-05-26 08:31:37 -0600323 response->error = key->formatted_key_material(request.key_format, &out_key, &size);
Shawn Willdenf268d742014-08-19 15:36:26 -0600324 if (response->error == KM_ERROR_OK) {
325 response->key_data = out_key.release();
326 response->key_data_length = size;
Shawn Willdenffd790c2014-08-18 21:20:06 -0600327 }
Shawn Willdenffd790c2014-08-18 21:20:06 -0600328}
329
Shawn Willdenb6837e72015-05-16 09:20:59 -0600330void AndroidKeymaster::ImportKey(const ImportKeyRequest& request, ImportKeyResponse* response) {
Shawn Willden437fbd12014-08-20 11:59:49 -0600331 if (response == NULL)
Shawn Willdenffd790c2014-08-18 21:20:06 -0600332 return;
Shawn Willdenffd790c2014-08-18 21:20:06 -0600333
Shawn Willdena278f612014-12-23 11:22:21 -0700334 keymaster_algorithm_t algorithm;
335 KeyFactory* factory = 0;
336 UniquePtr<Key> key;
337 if (!request.key_description.GetTagValue(TAG_ALGORITHM, &algorithm) ||
Shawn Willden06298102015-05-25 23:12:48 -0600338 !(factory = context_->GetKeyFactory(algorithm)))
Shawn Willdena278f612014-12-23 11:22:21 -0700339 response->error = KM_ERROR_UNSUPPORTED_ALGORITHM;
Shawn Willden0cb69422015-05-26 08:31:37 -0600340 else {
341 keymaster_key_blob_t key_material = {request.key_data, request.key_data_length};
342 KeymasterKeyBlob key_blob;
343 response->error = factory->ImportKey(request.key_description, request.key_format,
344 KeymasterKeyBlob(key_material), &key_blob,
345 &response->enforced, &response->unenforced);
346 if (response->error == KM_ERROR_OK)
347 response->key_blob = key_blob.release();
348 }
Shawn Willdenffd790c2014-08-18 21:20:06 -0600349}
350
Shawn Willden2beb6282015-05-20 16:36:24 -0600351keymaster_error_t AndroidKeymaster::DeleteKey(const DeleteKeyRequest& request) {
352 return context_->DeleteKey(KeymasterKeyBlob(request.key_blob));
353}
354
355keymaster_error_t AndroidKeymaster::DeleteAllKeys() {
356 return context_->DeleteAllKeys();
357}
358
Shawn Willden0cb69422015-05-26 08:31:37 -0600359keymaster_error_t AndroidKeymaster::LoadKey(const keymaster_key_blob_t& key_blob,
360 const AuthorizationSet& additional_params,
361 AuthorizationSet* hw_enforced,
362 AuthorizationSet* sw_enforced,
Shawn Willden06298102015-05-25 23:12:48 -0600363 const KeyFactory** factory, UniquePtr<Key>* key) {
Shawn Willden0cb69422015-05-26 08:31:37 -0600364 KeymasterKeyBlob key_material;
365 keymaster_error_t error = context_->ParseKeyBlob(KeymasterKeyBlob(key_blob), additional_params,
366 &key_material, hw_enforced, sw_enforced);
Shawn Willden437fbd12014-08-20 11:59:49 -0600367 if (error != KM_ERROR_OK)
368 return error;
369
Shawn Willden06298102015-05-25 23:12:48 -0600370 keymaster_algorithm_t algorithm;
371 *factory = GetKeyFactory(*context_, *hw_enforced, *sw_enforced, &algorithm, &error);
372 if (error != KM_ERROR_OK)
Shawn Willden437fbd12014-08-20 11:59:49 -0600373 return error;
Shawn Willden128ffe02014-08-06 12:31:33 -0600374
Shawn Willden06298102015-05-25 23:12:48 -0600375 return (*factory)->LoadKey(key_material, *hw_enforced, *sw_enforced, key);
Shawn Willden128ffe02014-08-06 12:31:33 -0600376}
377
Shawn Willden128ffe02014-08-06 12:31:33 -0600378} // namespace keymaster