blob: cb9c32ecbe18da74271e9623ccdeab7a2b6a03e7 [file] [log] [blame]
Shawn Willden128ffe02014-08-06 12:31:33 -06001/*
2 * Copyright (C) 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
17#include <gtest/gtest.h>
Shawn Willden76364712014-08-11 17:48:04 -060018
Shawn Willden128ffe02014-08-06 12:31:33 -060019#include <openssl/engine.h>
20
Shawn Willden76364712014-08-11 17:48:04 -060021#include "google_keymaster_test_utils.h"
Shawn Willden128ffe02014-08-06 12:31:33 -060022#include "google_keymaster_utils.h"
23#include "google_softkeymaster.h"
Shawn Willden76364712014-08-11 17:48:04 -060024#include "keymaster_tags.h"
Shawn Willden128ffe02014-08-06 12:31:33 -060025
26int main(int argc, char** argv) {
27 ::testing::InitGoogleTest(&argc, argv);
28 int result = RUN_ALL_TESTS();
29 // Clean up stuff OpenSSL leaves around, so Valgrind doesn't complain.
30 CRYPTO_cleanup_all_ex_data();
31 ERR_free_strings();
32 return result;
33}
34
35namespace keymaster {
36namespace test {
37
38class KeymasterTest : public testing::Test {
39 protected:
Shawn Willden1615f2e2014-08-13 10:37:40 -060040 KeymasterTest() : device(5) {
41 RAND_seed("foobar", 6);
Shawn Willden128ffe02014-08-06 12:31:33 -060042 }
43 ~KeymasterTest() {
44 }
45
46 GoogleSoftKeymaster device;
47};
48
49template <keymaster_tag_t Tag, typename KeymasterEnum>
50bool contains(const AuthorizationSet& set, TypedEnumTag<KM_ENUM, Tag, KeymasterEnum> tag,
51 KeymasterEnum val) {
52 int pos = set.find(tag);
53 return pos != -1 && set[pos].enumerated == val;
54}
55
56template <keymaster_tag_t Tag, typename KeymasterEnum>
57bool contains(const AuthorizationSet& set, TypedEnumTag<KM_ENUM_REP, Tag, KeymasterEnum> tag,
58 KeymasterEnum val) {
59 int pos = -1;
60 while ((pos = set.find(tag, pos)) != -1)
61 if (set[pos].enumerated == val)
62 return true;
63 return false;
64}
65
66template <keymaster_tag_t Tag>
67bool contains(const AuthorizationSet& set, TypedTag<KM_INT, Tag> tag, uint32_t val) {
68 int pos = set.find(tag);
69 return pos != -1 && set[pos].integer == val;
70}
71
72template <keymaster_tag_t Tag>
73bool contains(const AuthorizationSet& set, TypedTag<KM_INT_REP, Tag> tag, uint32_t val) {
74 int pos = -1;
75 while ((pos = set.find(tag, pos)) != -1)
76 if (set[pos].integer == val)
77 return true;
78 return false;
79}
80
81template <keymaster_tag_t Tag>
82bool contains(const AuthorizationSet& set, TypedTag<KM_LONG, Tag> tag, uint64_t val) {
83 int pos = set.find(tag);
84 return pos != -1 && set[pos].long_integer == val;
85}
86
87template <keymaster_tag_t Tag>
88bool contains(const AuthorizationSet& set, TypedTag<KM_BYTES, Tag> tag, const std::string& val) {
89 int pos = set.find(tag);
90 return pos != -1 &&
91 std::string(reinterpret_cast<const char*>(set[pos].blob.data),
92 set[pos].blob.data_length) == val;
93}
94
95inline bool contains(const AuthorizationSet& set, keymaster_tag_t tag) {
96 return set.find(tag) != -1;
97}
98
99typedef KeymasterTest CheckSupported;
100TEST_F(CheckSupported, SupportedAlgorithms) {
101 // Shouldn't blow up on NULL.
102 device.SupportedAlgorithms(NULL);
103
104 SupportedResponse<keymaster_algorithm_t> response;
105 device.SupportedAlgorithms(&response);
106 EXPECT_EQ(KM_ERROR_OK, response.error);
107 EXPECT_EQ(1U, response.results_length);
108 EXPECT_EQ(KM_ALGORITHM_RSA, response.results[0]);
109}
110
111TEST_F(CheckSupported, SupportedBlockModes) {
112 // Shouldn't blow up on NULL.
113 device.SupportedBlockModes(KM_ALGORITHM_RSA, NULL);
114
115 SupportedResponse<keymaster_block_mode_t> response;
116 device.SupportedBlockModes(KM_ALGORITHM_RSA, &response);
117 EXPECT_EQ(KM_ERROR_OK, response.error);
118 EXPECT_EQ(0U, response.results_length);
119
120 device.SupportedBlockModes(KM_ALGORITHM_DSA, &response);
121 EXPECT_EQ(KM_ERROR_UNSUPPORTED_ALGORITHM, response.error);
122}
123
124TEST_F(CheckSupported, SupportedPaddingModes) {
125 // Shouldn't blow up on NULL.
126 device.SupportedPaddingModes(KM_ALGORITHM_RSA, NULL);
127
128 SupportedResponse<keymaster_padding_t> response;
129 device.SupportedPaddingModes(KM_ALGORITHM_RSA, &response);
130 EXPECT_EQ(KM_ERROR_OK, response.error);
131 EXPECT_EQ(1U, response.results_length);
132 EXPECT_EQ(KM_PAD_NONE, response.results[0]);
133
134 device.SupportedPaddingModes(KM_ALGORITHM_DSA, &response);
135 EXPECT_EQ(KM_ERROR_UNSUPPORTED_ALGORITHM, response.error);
136}
137
138TEST_F(CheckSupported, SupportedDigests) {
139 // Shouldn't blow up on NULL.
140 device.SupportedDigests(KM_ALGORITHM_RSA, NULL);
141
142 SupportedResponse<keymaster_digest_t> response;
143 device.SupportedDigests(KM_ALGORITHM_RSA, &response);
144 EXPECT_EQ(KM_ERROR_OK, response.error);
145 EXPECT_EQ(1U, response.results_length);
146 EXPECT_EQ(KM_DIGEST_NONE, response.results[0]);
147
148 device.SupportedDigests(KM_ALGORITHM_DSA, &response);
149 EXPECT_EQ(KM_ERROR_UNSUPPORTED_ALGORITHM, response.error);
150}
151
152TEST_F(CheckSupported, SupportedImportFormats) {
153 // Shouldn't blow up on NULL.
154 device.SupportedImportFormats(KM_ALGORITHM_RSA, NULL);
155
156 SupportedResponse<keymaster_key_format_t> response;
157 device.SupportedImportFormats(KM_ALGORITHM_RSA, &response);
158 EXPECT_EQ(KM_ERROR_OK, response.error);
159 EXPECT_EQ(1U, response.results_length);
160 EXPECT_EQ(KM_KEY_FORMAT_PKCS8, response.results[0]);
161
162 device.SupportedImportFormats(KM_ALGORITHM_DSA, &response);
163 EXPECT_EQ(KM_ERROR_UNSUPPORTED_ALGORITHM, response.error);
164}
165
166TEST_F(CheckSupported, SupportedExportFormats) {
167 // Shouldn't blow up on NULL.
168 device.SupportedExportFormats(KM_ALGORITHM_RSA, NULL);
169
170 SupportedResponse<keymaster_key_format_t> response;
171 device.SupportedExportFormats(KM_ALGORITHM_RSA, &response);
172 EXPECT_EQ(KM_ERROR_OK, response.error);
173 EXPECT_EQ(1U, response.results_length);
174 EXPECT_EQ(KM_KEY_FORMAT_X509, response.results[0]);
175
176 device.SupportedExportFormats(KM_ALGORITHM_DSA, &response);
177 EXPECT_EQ(KM_ERROR_UNSUPPORTED_ALGORITHM, response.error);
178}
179
180typedef KeymasterTest NewKeyGeneration;
181TEST_F(NewKeyGeneration, Rsa) {
182 keymaster_key_param_t params[] = {
183 Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN),
184 Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY),
185 Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA),
Shawn Willden76364712014-08-11 17:48:04 -0600186 Authorization(TAG_KEY_SIZE, 256),
Shawn Willden128ffe02014-08-06 12:31:33 -0600187 Authorization(TAG_USER_ID, 7),
188 Authorization(TAG_USER_AUTH_ID, 8),
Shawn Willden76364712014-08-11 17:48:04 -0600189 Authorization(TAG_APPLICATION_ID, "app_id", 6),
190 Authorization(TAG_APPLICATION_DATA, "app_data", 8),
Shawn Willden128ffe02014-08-06 12:31:33 -0600191 Authorization(TAG_AUTH_TIMEOUT, 300),
192 };
193 GenerateKeyRequest req;
194 req.key_description.Reinitialize(params, array_length(params));
195 GenerateKeyResponse rsp;
196
197 device.GenerateKey(req, &rsp);
198
199 ASSERT_EQ(KM_ERROR_OK, rsp.error);
200 EXPECT_EQ(0U, rsp.enforced.size());
Shawn Willden8d336ae2014-08-09 15:47:05 -0600201 EXPECT_EQ(12U, rsp.enforced.SerializedSize());
202 EXPECT_GT(rsp.unenforced.SerializedSize(), 12U);
Shawn Willden128ffe02014-08-06 12:31:33 -0600203
204 // Check specified tags are all present in unenforced characteristics
205 EXPECT_TRUE(contains(rsp.unenforced, TAG_PURPOSE, KM_PURPOSE_SIGN));
206 EXPECT_TRUE(contains(rsp.unenforced, TAG_PURPOSE, KM_PURPOSE_VERIFY));
207
208 EXPECT_TRUE(contains(rsp.unenforced, TAG_ALGORITHM, KM_ALGORITHM_RSA));
209
210 EXPECT_TRUE(contains(rsp.unenforced, TAG_USER_ID, 7));
211 EXPECT_TRUE(contains(rsp.unenforced, TAG_USER_AUTH_ID, 8));
Shawn Willden76364712014-08-11 17:48:04 -0600212 EXPECT_TRUE(contains(rsp.unenforced, TAG_KEY_SIZE, 256));
Shawn Willden128ffe02014-08-06 12:31:33 -0600213 EXPECT_TRUE(contains(rsp.unenforced, TAG_AUTH_TIMEOUT, 300));
214
Shawn Willden39b970b2014-08-11 09:11:21 -0600215 // Verify that App ID, App data and ROT are NOT included.
216 EXPECT_FALSE(contains(rsp.unenforced, TAG_ROOT_OF_TRUST));
217 EXPECT_FALSE(contains(rsp.unenforced, TAG_APPLICATION_ID));
218 EXPECT_FALSE(contains(rsp.unenforced, TAG_APPLICATION_DATA));
219
Shawn Willden128ffe02014-08-06 12:31:33 -0600220 // Just for giggles, check that some unexpected tags/values are NOT present.
221 EXPECT_FALSE(contains(rsp.unenforced, TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
222 EXPECT_FALSE(contains(rsp.unenforced, TAG_PURPOSE, KM_PURPOSE_DECRYPT));
223 EXPECT_FALSE(contains(rsp.unenforced, TAG_AUTH_TIMEOUT, 301));
224 EXPECT_FALSE(contains(rsp.unenforced, TAG_RESCOPE_AUTH_TIMEOUT));
225
226 // Now check that unspecified, defaulted tags are correct.
227 EXPECT_TRUE(contains(rsp.unenforced, TAG_RSA_PUBLIC_EXPONENT, 65537));
228 EXPECT_TRUE(contains(rsp.unenforced, TAG_ORIGIN, KM_ORIGIN_SOFTWARE));
229 EXPECT_TRUE(contains(rsp.unenforced, KM_TAG_CREATION_DATETIME));
Shawn Willden128ffe02014-08-06 12:31:33 -0600230}
231
Shawn Willden76364712014-08-11 17:48:04 -0600232typedef KeymasterTest GetKeyCharacteristics;
233TEST_F(GetKeyCharacteristics, SimpleRsa) {
234 keymaster_key_param_t params[] = {
235 Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN),
236 Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY),
237 Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA),
238 Authorization(TAG_KEY_SIZE, 256),
239 Authorization(TAG_USER_ID, 7),
240 Authorization(TAG_USER_AUTH_ID, 8),
Shawn Willden1615f2e2014-08-13 10:37:40 -0600241 Authorization(TAG_APPLICATION_ID, "app_id", 6),
Shawn Willden76364712014-08-11 17:48:04 -0600242 Authorization(TAG_AUTH_TIMEOUT, 300),
243 };
244
245 GenerateKeyRequest gen_req;
246 gen_req.key_description.Reinitialize(params, array_length(params));
247 GenerateKeyResponse gen_rsp;
248
249 device.GenerateKey(gen_req, &gen_rsp);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600250 ASSERT_EQ(KM_ERROR_OK, gen_rsp.error);
Shawn Willden76364712014-08-11 17:48:04 -0600251
252 GetKeyCharacteristicsRequest req;
253 req.key_blob = gen_rsp.key_blob;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600254 req.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
Shawn Willden76364712014-08-11 17:48:04 -0600255
256 GetKeyCharacteristicsResponse rsp;
257 device.GetKeyCharacteristics(req, &rsp);
258 ASSERT_EQ(KM_ERROR_OK, rsp.error);
259
260 EXPECT_EQ(gen_rsp.enforced, rsp.enforced);
261 EXPECT_EQ(gen_rsp.unenforced, rsp.unenforced);
262}
263
Shawn Willden1615f2e2014-08-13 10:37:40 -0600264class SigningOperationsTest : public KeymasterTest {
265 protected:
266 keymaster_key_blob_t* GenerateKey(keymaster_digest_t digest, keymaster_padding_t padding,
267 uint32_t key_size) {
268 keymaster_key_param_t params[] = {
269 Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN),
270 Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY),
271 Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA),
272 Authorization(TAG_KEY_SIZE, key_size),
273 Authorization(TAG_USER_ID, 7),
274 Authorization(TAG_USER_AUTH_ID, 8),
275 Authorization(TAG_APPLICATION_ID, "app_id", 6),
276 Authorization(TAG_AUTH_TIMEOUT, 300),
277 };
278 GenerateKeyRequest generate_request;
279 generate_request.key_description.Reinitialize(params, array_length(params));
Shawn Willden43e999e2014-08-13 13:29:50 -0600280 if (static_cast<int>(digest) != -1)
Shawn Willden1615f2e2014-08-13 10:37:40 -0600281 generate_request.key_description.push_back(TAG_DIGEST, digest);
Shawn Willden43e999e2014-08-13 13:29:50 -0600282 if (static_cast<int>(padding) != -1)
Shawn Willden1615f2e2014-08-13 10:37:40 -0600283 generate_request.key_description.push_back(TAG_PADDING, padding);
284 device.GenerateKey(generate_request, &generate_response_);
285 EXPECT_EQ(KM_ERROR_OK, generate_response_.error);
286
287 // This is safe because generate_response_ lives as long as the test and will keep the key
288 // blob around.
289 return &generate_response_.key_blob;
290 }
291
292 private:
293 GenerateKeyResponse generate_response_;
294};
295
296TEST_F(SigningOperationsTest, RsaSuccess) {
297 keymaster_key_blob_t* key = GenerateKey(KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
298 ASSERT_TRUE(key != NULL);
299
300 BeginOperationRequest begin_request;
301 BeginOperationResponse begin_response;
302 begin_request.key_blob = *key;
303 begin_request.purpose = KM_PURPOSE_SIGN;
304 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
305
306 device.BeginOperation(begin_request, &begin_response);
307 ASSERT_EQ(KM_ERROR_OK, begin_response.error);
308
309 UpdateOperationRequest update_request;
310 UpdateOperationResponse update_response;
311 update_request.op_handle = begin_response.op_handle;
312 update_request.input.Reinitialize("012345678901234567890123456789012", 32);
313 EXPECT_EQ(32U, update_request.input.available_read());
314
315 device.UpdateOperation(update_request, &update_response);
316 ASSERT_EQ(KM_ERROR_OK, update_response.error);
317 EXPECT_EQ(0U, update_response.output.available_read());
318
Shawn Willden43e999e2014-08-13 13:29:50 -0600319 FinishOperationRequest finish_request;
320 finish_request.op_handle = begin_response.op_handle;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600321 FinishOperationResponse finish_response;
Shawn Willden43e999e2014-08-13 13:29:50 -0600322 device.FinishOperation(finish_request, &finish_response);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600323 ASSERT_EQ(KM_ERROR_OK, finish_response.error);
Shawn Willden43e999e2014-08-13 13:29:50 -0600324 EXPECT_GT(finish_response.output.available_read(), 0U);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600325
326 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device.AbortOperation(begin_response.op_handle));
327}
328
329TEST_F(SigningOperationsTest, RsaAbort) {
330 keymaster_key_blob_t* key = GenerateKey(KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
331 ASSERT_TRUE(key != NULL);
332
333 BeginOperationRequest begin_request;
334 BeginOperationResponse begin_response;
335 begin_request.key_blob = *key;
336 begin_request.purpose = KM_PURPOSE_SIGN;
337 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
338
339 device.BeginOperation(begin_request, &begin_response);
340 ASSERT_EQ(KM_ERROR_OK, begin_response.error);
341
342 EXPECT_EQ(KM_ERROR_OK, device.AbortOperation(begin_response.op_handle));
343
344 // Another abort should fail
345 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device.AbortOperation(begin_response.op_handle));
346}
347
348TEST_F(SigningOperationsTest, RsaUnsupportedDigest) {
349 keymaster_key_blob_t* key = GenerateKey(KM_DIGEST_SHA_2_256, KM_PAD_NONE, 256 /* key size */);
350 ASSERT_TRUE(key != NULL);
351
352 BeginOperationRequest begin_request;
353 BeginOperationResponse begin_response;
354 begin_request.purpose = KM_PURPOSE_SIGN;
355 begin_request.key_blob = *key;
356 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
357
358 device.BeginOperation(begin_request, &begin_response);
359 ASSERT_EQ(KM_ERROR_UNSUPPORTED_DIGEST, begin_response.error);
360
361 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device.AbortOperation(begin_response.op_handle));
362}
363
364TEST_F(SigningOperationsTest, RsaUnsupportedPadding) {
365 keymaster_key_blob_t* key = GenerateKey(KM_DIGEST_NONE, KM_PAD_RSA_OAEP, 256 /* key size */);
366 ASSERT_TRUE(key != NULL);
367
368 BeginOperationRequest begin_request;
369 BeginOperationResponse begin_response;
370 begin_request.purpose = KM_PURPOSE_SIGN;
371 begin_request.key_blob = *key;
372 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
373
374 device.BeginOperation(begin_request, &begin_response);
375 ASSERT_EQ(KM_ERROR_UNSUPPORTED_PADDING_MODE, begin_response.error);
376
377 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device.AbortOperation(begin_response.op_handle));
378}
379
380TEST_F(SigningOperationsTest, RsaNoDigest) {
381 keymaster_key_blob_t* key =
382 GenerateKey(static_cast<keymaster_digest_t>(-1), KM_PAD_NONE, 256 /* key size */);
383 ASSERT_TRUE(key != NULL);
384
385 BeginOperationRequest begin_request;
386 BeginOperationResponse begin_response;
387 begin_request.purpose = KM_PURPOSE_SIGN;
388 begin_request.key_blob = *key;
389 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
390
391 device.BeginOperation(begin_request, &begin_response);
392 ASSERT_EQ(KM_ERROR_UNSUPPORTED_DIGEST, begin_response.error);
393
394 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device.AbortOperation(begin_response.op_handle));
395}
396
397TEST_F(SigningOperationsTest, RsaNoPadding) {
398 keymaster_key_blob_t* key =
399 GenerateKey(KM_DIGEST_NONE, static_cast<keymaster_padding_t>(-1), 256 /* key size */);
400 ASSERT_TRUE(key != NULL);
401
402 BeginOperationRequest begin_request;
403 BeginOperationResponse begin_response;
404 begin_request.purpose = KM_PURPOSE_SIGN;
405 begin_request.key_blob = *key;
406 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
407
408 device.BeginOperation(begin_request, &begin_response);
409 ASSERT_EQ(KM_ERROR_UNSUPPORTED_PADDING_MODE, begin_response.error);
410
411 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device.AbortOperation(begin_response.op_handle));
412}
413
414TEST_F(SigningOperationsTest, RsaTooShortMessage) {
415 keymaster_key_blob_t* key = GenerateKey(KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
416 ASSERT_TRUE(key != NULL);
417
418 BeginOperationRequest begin_request;
419 BeginOperationResponse begin_response;
420 begin_request.key_blob = *key;
421 begin_request.purpose = KM_PURPOSE_SIGN;
422 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
423
424 device.BeginOperation(begin_request, &begin_response);
425 ASSERT_EQ(KM_ERROR_OK, begin_response.error);
426
427 UpdateOperationRequest update_request;
428 UpdateOperationResponse update_response;
429 update_request.op_handle = begin_response.op_handle;
430 update_request.input.Reinitialize("01234567890123456789012345678901", 31);
431 EXPECT_EQ(31U, update_request.input.available_read());
432
433 device.UpdateOperation(update_request, &update_response);
434 ASSERT_EQ(KM_ERROR_OK, update_response.error);
435 EXPECT_EQ(0U, update_response.output.available_read());
436
Shawn Willden43e999e2014-08-13 13:29:50 -0600437 FinishOperationRequest finish_request;
438 finish_request.op_handle = begin_response.op_handle;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600439 FinishOperationResponse finish_response;
Shawn Willden43e999e2014-08-13 13:29:50 -0600440 device.FinishOperation(finish_request, &finish_response);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600441 ASSERT_EQ(KM_ERROR_INVALID_INPUT_LENGTH, finish_response.error);
Shawn Willden43e999e2014-08-13 13:29:50 -0600442 EXPECT_EQ(0U, finish_response.output.available_read());
443
444 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device.AbortOperation(begin_response.op_handle));
445}
446
447class VerificationOperationsTest : public KeymasterTest {
448 protected:
449 VerificationOperationsTest() {
450 generate_response_.error = KM_ERROR_UNKNOWN_ERROR;
451 finish_response_.error = KM_ERROR_UNKNOWN_ERROR;
452 }
453
454 void GenerateKey(keymaster_digest_t digest, keymaster_padding_t padding,
455 uint32_t key_size) {
456 keymaster_key_param_t params[] = {
457 Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN),
458 Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY),
459 Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA),
460 Authorization(TAG_KEY_SIZE, key_size),
461 Authorization(TAG_USER_ID, 7),
462 Authorization(TAG_USER_AUTH_ID, 8),
463 Authorization(TAG_APPLICATION_ID, "app_id", 6),
464 Authorization(TAG_AUTH_TIMEOUT, 300),
465 };
466 GenerateKeyRequest generate_request;
467 generate_request.key_description.Reinitialize(params, array_length(params));
468 if (static_cast<int>(digest) != -1)
469 generate_request.key_description.push_back(TAG_DIGEST, digest);
470 if (static_cast<int>(padding) != -1)
471 generate_request.key_description.push_back(TAG_PADDING, padding);
472 device.GenerateKey(generate_request, &generate_response_);
473 EXPECT_EQ(KM_ERROR_OK, generate_response_.error);
474
475 BeginOperationRequest begin_request;
476 BeginOperationResponse begin_response;
477 begin_request.key_blob = generate_response_.key_blob;
478 begin_request.purpose = KM_PURPOSE_SIGN;
479 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
480
481 device.BeginOperation(begin_request, &begin_response);
482 ASSERT_EQ(KM_ERROR_OK, begin_response.error);
483
484 UpdateOperationRequest update_request;
485 UpdateOperationResponse update_response;
486 update_request.op_handle = begin_response.op_handle;
487 update_request.input.Reinitialize("012345678901234567890123456789012", 32);
488 EXPECT_EQ(32U, update_request.input.available_read());
489
490 device.UpdateOperation(update_request, &update_response);
491 ASSERT_EQ(KM_ERROR_OK, update_response.error);
492 EXPECT_EQ(0U, update_response.output.available_read());
493
494 FinishOperationRequest finish_request;
495 finish_request.op_handle = begin_response.op_handle;
496 device.FinishOperation(finish_request, &finish_response_);
497 ASSERT_EQ(KM_ERROR_OK, finish_response_.error);
498 EXPECT_GT(finish_response_.output.available_read(), 0U);
499 }
500
501 keymaster_key_blob_t* key_blob() {
502 if (generate_response_.error == KM_ERROR_OK)
503 return &generate_response_.key_blob;
504 return NULL;
505 }
506
507 Buffer* signature() {
508 if (finish_response_.error == KM_ERROR_OK)
509 return &finish_response_.output;
510 return NULL;
511 }
512
513 private:
514 GenerateKeyResponse generate_response_;
515 FinishOperationResponse finish_response_;
516};
517
518TEST_F(VerificationOperationsTest, RsaSuccess) {
519 GenerateKey(KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
520 ASSERT_TRUE(key_blob() != NULL);
521 ASSERT_TRUE(signature() != NULL);
522
523 BeginOperationRequest begin_request;
524 BeginOperationResponse begin_response;
525 begin_request.key_blob = *key_blob();
526 begin_request.purpose = KM_PURPOSE_VERIFY;
527 begin_request.additional_params.push_back(TAG_APPLICATION_ID, "app_id", 6);
528
529 device.BeginOperation(begin_request, &begin_response);
530 ASSERT_EQ(KM_ERROR_OK, begin_response.error);
531
532 UpdateOperationRequest update_request;
533 UpdateOperationResponse update_response;
534 update_request.op_handle = begin_response.op_handle;
535 update_request.input.Reinitialize("012345678901234567890123456789012", 32);
536 EXPECT_EQ(32U, update_request.input.available_read());
537
538 device.UpdateOperation(update_request, &update_response);
539 ASSERT_EQ(KM_ERROR_OK, update_response.error);
540 EXPECT_EQ(0U, update_response.output.available_read());
541
542 FinishOperationRequest finish_request;
543 finish_request.op_handle = begin_response.op_handle;
544 finish_request.signature.Reinitialize(*signature());
545 FinishOperationResponse finish_response;
546 device.FinishOperation(finish_request, &finish_response);
547 ASSERT_EQ(KM_ERROR_OK, finish_response.error);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600548 EXPECT_EQ(0U, finish_response.output.available_read());
549
550 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device.AbortOperation(begin_response.op_handle));
551}
552
Shawn Willden128ffe02014-08-06 12:31:33 -0600553} // namespace test
554} // namespace keymaster