blob: 6c672be5593882443fc8c08152849ad6d07dd02f [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
Shawn Willden437fbd12014-08-20 11:59:49 -060017#include <string>
18#include <fstream>
19
Shawn Willden128ffe02014-08-06 12:31:33 -060020#include <gtest/gtest.h>
Shawn Willden76364712014-08-11 17:48:04 -060021
Shawn Willden128ffe02014-08-06 12:31:33 -060022#include <openssl/engine.h>
23
Shawn Willden98d9b922014-08-26 08:14:10 -060024#include <keymaster/google_keymaster_utils.h>
25#include <keymaster/keymaster_tags.h>
26
Shawn Willden76364712014-08-11 17:48:04 -060027#include "google_keymaster_test_utils.h"
Shawn Willden2079ae82015-01-22 13:42:31 -070028#include "soft_keymaster_device.h"
Shawn Willden128ffe02014-08-06 12:31:33 -060029
Shawn Willden437fbd12014-08-20 11:59:49 -060030using std::string;
31using std::ifstream;
32using std::istreambuf_iterator;
33
Shawn Willden128ffe02014-08-06 12:31:33 -060034int main(int argc, char** argv) {
35 ::testing::InitGoogleTest(&argc, argv);
36 int result = RUN_ALL_TESTS();
37 // Clean up stuff OpenSSL leaves around, so Valgrind doesn't complain.
38 CRYPTO_cleanup_all_ex_data();
Shawn Willden7c0a82b2014-09-17 12:57:32 -060039 ERR_remove_thread_state(NULL);
Shawn Willden128ffe02014-08-06 12:31:33 -060040 ERR_free_strings();
41 return result;
42}
43
44namespace keymaster {
45namespace test {
46
Shawn Willden6bbe6782014-09-18 11:26:15 -060047// Note that these DSA generator, p and q values must match the values from dsa_privkey_pk8.der.
48const uint8_t dsa_g[] = {
49 0x19, 0x1C, 0x71, 0xFD, 0xE0, 0x03, 0x0C, 0x43, 0xD9, 0x0B, 0xF6, 0xCD, 0xD6, 0xA9, 0x70, 0xE7,
50 0x37, 0x86, 0x3A, 0x78, 0xE9, 0xA7, 0x47, 0xA7, 0x47, 0x06, 0x88, 0xB1, 0xAF, 0xD7, 0xF3, 0xF1,
51 0xA1, 0xD7, 0x00, 0x61, 0x28, 0x88, 0x31, 0x48, 0x60, 0xD8, 0x11, 0xEF, 0xA5, 0x24, 0x1A, 0x81,
52 0xC4, 0x2A, 0xE2, 0xEA, 0x0E, 0x36, 0xD2, 0xD2, 0x05, 0x84, 0x37, 0xCF, 0x32, 0x7D, 0x09, 0xE6,
53 0x0F, 0x8B, 0x0C, 0xC8, 0xC2, 0xA4, 0xB1, 0xDC, 0x80, 0xCA, 0x68, 0xDF, 0xAF, 0xD2, 0x90, 0xC0,
54 0x37, 0x58, 0x54, 0x36, 0x8F, 0x49, 0xB8, 0x62, 0x75, 0x8B, 0x48, 0x47, 0xC0, 0xBE, 0xF7, 0x9A,
55 0x92, 0xA6, 0x68, 0x05, 0xDA, 0x9D, 0xAF, 0x72, 0x9A, 0x67, 0xB3, 0xB4, 0x14, 0x03, 0xAE, 0x4F,
56 0x4C, 0x76, 0xB9, 0xD8, 0x64, 0x0A, 0xBA, 0x3B, 0xA8, 0x00, 0x60, 0x4D, 0xAE, 0x81, 0xC3, 0xC5,
57};
58const uint8_t dsa_p[] = {
59 0xA3, 0xF3, 0xE9, 0xB6, 0x7E, 0x7D, 0x88, 0xF6, 0xB7, 0xE5, 0xF5, 0x1F, 0x3B, 0xEE, 0xAC, 0xD7,
60 0xAD, 0xBC, 0xC9, 0xD1, 0x5A, 0xF8, 0x88, 0xC4, 0xEF, 0x6E, 0x3D, 0x74, 0x19, 0x74, 0xE7, 0xD8,
61 0xE0, 0x26, 0x44, 0x19, 0x86, 0xAF, 0x19, 0xDB, 0x05, 0xE9, 0x3B, 0x8B, 0x58, 0x58, 0xDE, 0xE5,
62 0x4F, 0x48, 0x15, 0x01, 0xEA, 0xE6, 0x83, 0x52, 0xD7, 0xC1, 0x21, 0xDF, 0xB9, 0xB8, 0x07, 0x66,
63 0x50, 0xFB, 0x3A, 0x0C, 0xB3, 0x85, 0xEE, 0xBB, 0x04, 0x5F, 0xC2, 0x6D, 0x6D, 0x95, 0xFA, 0x11,
64 0x93, 0x1E, 0x59, 0x5B, 0xB1, 0x45, 0x8D, 0xE0, 0x3D, 0x73, 0xAA, 0xF2, 0x41, 0x14, 0x51, 0x07,
65 0x72, 0x3D, 0xA2, 0xF7, 0x58, 0xCD, 0x11, 0xA1, 0x32, 0xCF, 0xDA, 0x42, 0xB7, 0xCC, 0x32, 0x80,
66 0xDB, 0x87, 0x82, 0xEC, 0x42, 0xDB, 0x5A, 0x55, 0x24, 0x24, 0xA2, 0xD1, 0x55, 0x29, 0xAD, 0xEB,
67};
68const uint8_t dsa_q[] = {
69 0xEB, 0xEA, 0x17, 0xD2, 0x09, 0xB3, 0xD7, 0x21, 0x9A, 0x21,
70 0x07, 0x82, 0x8F, 0xAB, 0xFE, 0x88, 0x71, 0x68, 0xF7, 0xE3,
71};
72
Shawn Willden128ffe02014-08-06 12:31:33 -060073class KeymasterTest : public testing::Test {
74 protected:
Shawn Willden2079ae82015-01-22 13:42:31 -070075 KeymasterTest() : device_(new StdoutLogger), characteristics_(NULL) {
76 blob_.key_material = NULL;
77 RAND_seed("foobar", 6);
78 }
79 ~KeymasterTest() {
80 FreeCharacteristics();
81 FreeKeyBlob();
Shawn Willdend0772312014-09-18 12:27:57 -060082 }
83
Shawn Willden2079ae82015-01-22 13:42:31 -070084 keymaster_device* device() { return reinterpret_cast<keymaster_device*>(device_.hw_device()); }
85
86 template <typename T> void ExpectContains(T val, T* vals, size_t len) {
87 EXPECT_EQ(1U, len);
88 EXPECT_EQ(val, vals[0]);
Shawn Willdend0772312014-09-18 12:27:57 -060089 }
90
Shawn Willden2079ae82015-01-22 13:42:31 -070091 void FreeCharacteristics() {
92 keymaster_free_characteristics(characteristics_);
93 free(characteristics_);
94 characteristics_ = NULL;
95 }
96
97 void FreeKeyBlob() {
98 free(const_cast<uint8_t*>(blob_.key_material));
99 blob_.key_material = NULL;
100 }
101
102 SoftKeymasterDevice device_;
103
104 AuthorizationSet params_;
105 keymaster_key_blob_t blob_;
106 keymaster_key_characteristics_t* characteristics_;
Shawn Willden128ffe02014-08-06 12:31:33 -0600107};
108
Shawn Willden128ffe02014-08-06 12:31:33 -0600109typedef KeymasterTest CheckSupported;
110TEST_F(CheckSupported, SupportedAlgorithms) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700111 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
112 device()->get_supported_algorithms(device(), NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600113
Shawn Willden2079ae82015-01-22 13:42:31 -0700114 size_t len;
115 keymaster_algorithm_t* algorithms;
116 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_algorithms(device(), &algorithms, &len));
117 ASSERT_EQ(4U, len);
118 EXPECT_EQ(KM_ALGORITHM_RSA, algorithms[0]);
119 EXPECT_EQ(KM_ALGORITHM_DSA, algorithms[1]);
120 EXPECT_EQ(KM_ALGORITHM_ECDSA, algorithms[2]);
121 EXPECT_EQ(KM_ALGORITHM_AES, algorithms[3]);
122
123 free(algorithms);
Shawn Willden128ffe02014-08-06 12:31:33 -0600124}
125
126TEST_F(CheckSupported, SupportedBlockModes) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700127 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
128 device()->get_supported_block_modes(device(), KM_ALGORITHM_RSA, KM_PURPOSE_ENCRYPT,
129 NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600130
Shawn Willden2079ae82015-01-22 13:42:31 -0700131 size_t len;
132 keymaster_block_mode_t* modes;
133 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
134 device()->get_supported_block_modes(device(), KM_ALGORITHM_RSA, KM_PURPOSE_ENCRYPT,
135 &modes, &len));
Shawn Willden128ffe02014-08-06 12:31:33 -0600136
Shawn Willden2079ae82015-01-22 13:42:31 -0700137 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
138 device()->get_supported_block_modes(device(), KM_ALGORITHM_DSA, KM_PURPOSE_ENCRYPT,
139 &modes, &len));
Shawn Willden28e41472014-08-18 13:35:22 -0600140
Shawn Willden2079ae82015-01-22 13:42:31 -0700141 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
142 device()->get_supported_block_modes(device(), KM_ALGORITHM_ECDSA, KM_PURPOSE_ENCRYPT,
143 &modes, &len));
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600144
Shawn Willden2079ae82015-01-22 13:42:31 -0700145 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
146 device()->get_supported_block_modes(device(), KM_ALGORITHM_AES, KM_PURPOSE_ENCRYPT,
147 &modes, &len));
Shawn Willden128ffe02014-08-06 12:31:33 -0600148}
149
150TEST_F(CheckSupported, SupportedPaddingModes) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700151 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
152 device()->get_supported_padding_modes(device(), KM_ALGORITHM_RSA, KM_PURPOSE_ENCRYPT,
153 NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600154
Shawn Willden2079ae82015-01-22 13:42:31 -0700155 size_t len;
156 keymaster_padding_t* modes;
157 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_padding_modes(device(), KM_ALGORITHM_RSA,
158 KM_PURPOSE_SIGN, &modes, &len));
159 ExpectContains(KM_PAD_NONE, modes, len);
160 free(modes);
Shawn Willden128ffe02014-08-06 12:31:33 -0600161
Shawn Willden2079ae82015-01-22 13:42:31 -0700162 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_padding_modes(device(), KM_ALGORITHM_DSA,
163 KM_PURPOSE_SIGN, &modes, &len));
164 ExpectContains(KM_PAD_NONE, modes, len);
165 free(modes);
Shawn Willden28e41472014-08-18 13:35:22 -0600166
Shawn Willden2079ae82015-01-22 13:42:31 -0700167 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_padding_modes(device(), KM_ALGORITHM_ECDSA,
168 KM_PURPOSE_SIGN, &modes, &len));
169 ExpectContains(KM_PAD_NONE, modes, len);
170 free(modes);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600171
Shawn Willden2079ae82015-01-22 13:42:31 -0700172 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_padding_modes(device(), KM_ALGORITHM_AES,
173 KM_PURPOSE_SIGN, &modes, &len));
174 EXPECT_EQ(0, len);
175 free(modes);
Shawn Willden128ffe02014-08-06 12:31:33 -0600176}
177
178TEST_F(CheckSupported, SupportedDigests) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700179 EXPECT_EQ(
180 KM_ERROR_OUTPUT_PARAMETER_NULL,
181 device()->get_supported_digests(device(), KM_ALGORITHM_RSA, KM_PURPOSE_SIGN, NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600182
Shawn Willden2079ae82015-01-22 13:42:31 -0700183 size_t len;
184 keymaster_digest_t* digests;
185 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_digests(device(), KM_ALGORITHM_RSA,
186 KM_PURPOSE_SIGN, &digests, &len));
187 ExpectContains(KM_DIGEST_NONE, digests, len);
188 free(digests);
Shawn Willden128ffe02014-08-06 12:31:33 -0600189
Shawn Willden2079ae82015-01-22 13:42:31 -0700190 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_digests(device(), KM_ALGORITHM_DSA,
191 KM_PURPOSE_SIGN, &digests, &len));
192 ExpectContains(KM_DIGEST_NONE, digests, len);
193 free(digests);
Shawn Willden28e41472014-08-18 13:35:22 -0600194
Shawn Willden2079ae82015-01-22 13:42:31 -0700195 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_digests(device(), KM_ALGORITHM_ECDSA,
196 KM_PURPOSE_SIGN, &digests, &len));
197 ExpectContains(KM_DIGEST_NONE, digests, len);
198 free(digests);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600199
Shawn Willden2079ae82015-01-22 13:42:31 -0700200 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_digests(device(), KM_ALGORITHM_AES,
201 KM_PURPOSE_SIGN, &digests, &len));
202 EXPECT_EQ(0, len);
203 free(digests);
Shawn Willden128ffe02014-08-06 12:31:33 -0600204}
205
206TEST_F(CheckSupported, SupportedImportFormats) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700207 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
208 device()->get_supported_import_formats(device(), KM_ALGORITHM_RSA, NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600209
Shawn Willden2079ae82015-01-22 13:42:31 -0700210 size_t len;
211 keymaster_key_format_t* formats;
212 EXPECT_EQ(KM_ERROR_OK,
213 device()->get_supported_import_formats(device(), KM_ALGORITHM_RSA, &formats, &len));
214 ExpectContains(KM_KEY_FORMAT_PKCS8, formats, len);
215 free(formats);
Shawn Willden128ffe02014-08-06 12:31:33 -0600216
Shawn Willden2079ae82015-01-22 13:42:31 -0700217 EXPECT_EQ(KM_ERROR_OK,
218 device()->get_supported_import_formats(device(), KM_ALGORITHM_DSA, &formats, &len));
219 ExpectContains(KM_KEY_FORMAT_PKCS8, formats, len);
220 free(formats);
Shawn Willden28e41472014-08-18 13:35:22 -0600221
Shawn Willden2079ae82015-01-22 13:42:31 -0700222 EXPECT_EQ(KM_ERROR_OK,
223 device()->get_supported_import_formats(device(), KM_ALGORITHM_ECDSA, &formats, &len));
224 ExpectContains(KM_KEY_FORMAT_PKCS8, formats, len);
225 free(formats);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600226
Shawn Willden2079ae82015-01-22 13:42:31 -0700227 EXPECT_EQ(KM_ERROR_OK,
228 device()->get_supported_import_formats(device(), KM_ALGORITHM_AES, &formats, &len));
229 EXPECT_EQ(0, len);
230 free(formats);
Shawn Willden128ffe02014-08-06 12:31:33 -0600231}
232
233TEST_F(CheckSupported, SupportedExportFormats) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700234 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
235 device()->get_supported_export_formats(device(), KM_ALGORITHM_RSA, NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600236
Shawn Willden2079ae82015-01-22 13:42:31 -0700237 size_t len;
238 keymaster_key_format_t* formats;
239 EXPECT_EQ(KM_ERROR_OK,
240 device()->get_supported_export_formats(device(), KM_ALGORITHM_RSA, &formats, &len));
241 ExpectContains(KM_KEY_FORMAT_X509, formats, len);
242 free(formats);
Shawn Willden128ffe02014-08-06 12:31:33 -0600243
Shawn Willden2079ae82015-01-22 13:42:31 -0700244 EXPECT_EQ(KM_ERROR_OK,
245 device()->get_supported_export_formats(device(), KM_ALGORITHM_DSA, &formats, &len));
246 ExpectContains(KM_KEY_FORMAT_X509, formats, len);
247 free(formats);
Shawn Willden28e41472014-08-18 13:35:22 -0600248
Shawn Willden2079ae82015-01-22 13:42:31 -0700249 EXPECT_EQ(KM_ERROR_OK,
250 device()->get_supported_export_formats(device(), KM_ALGORITHM_ECDSA, &formats, &len));
251 ExpectContains(KM_KEY_FORMAT_X509, formats, len);
252 free(formats);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600253
Shawn Willden2079ae82015-01-22 13:42:31 -0700254 EXPECT_EQ(KM_ERROR_OK,
255 device()->get_supported_export_formats(device(), KM_ALGORITHM_AES, &formats, &len));
256 EXPECT_EQ(0, len);
257 free(formats);
Shawn Willden128ffe02014-08-06 12:31:33 -0600258}
259
Shawn Willdend0772312014-09-18 12:27:57 -0600260keymaster_key_param_t key_generation_base_params[] = {
Shawn Willden3809b932014-12-02 06:59:46 -0700261 Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN), Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY),
262 Authorization(TAG_USER_ID, 7), Authorization(TAG_USER_AUTH_ID, 8),
Shawn Willdend0772312014-09-18 12:27:57 -0600263 Authorization(TAG_APPLICATION_ID, "app_id", 6),
Shawn Willden3809b932014-12-02 06:59:46 -0700264 Authorization(TAG_APPLICATION_DATA, "app_data", 8), Authorization(TAG_AUTH_TIMEOUT, 300),
Shawn Willdend0772312014-09-18 12:27:57 -0600265};
266
Shawn Willden2079ae82015-01-22 13:42:31 -0700267TEST_F(KeymasterTest, TestFlags) {
268 EXPECT_TRUE(device()->flags & KEYMASTER_SOFTWARE_ONLY);
269 EXPECT_TRUE(device()->flags & KEYMASTER_BLOBS_ARE_STANDALONE);
270 EXPECT_FALSE(device()->flags & KEYMASTER_SUPPORTS_DSA);
271 EXPECT_TRUE(device()->flags & KEYMASTER_SUPPORTS_EC);
272}
273
274typedef KeymasterTest OldKeyGeneration;
275
276TEST_F(OldKeyGeneration, Rsa) {
277 keymaster_rsa_keygen_params_t params = {.modulus_size = 256, .public_exponent = 3};
278 uint8_t* key_blob;
279 size_t key_blob_length;
280 EXPECT_EQ(0,
281 device()->generate_keypair(device(), TYPE_RSA, &params, &key_blob, &key_blob_length));
282 EXPECT_GT(key_blob_length, 0);
283
284 free(key_blob);
285}
286
287TEST_F(OldKeyGeneration, Ecdsa) {
288
289 keymaster_ec_keygen_params_t params = {.field_size = 256};
290 uint8_t* key_blob;
291 size_t key_blob_length;
292 EXPECT_EQ(0,
293 device()->generate_keypair(device(), TYPE_EC, &params, &key_blob, &key_blob_length));
294 EXPECT_GT(key_blob_length, 0);
295
296 free(key_blob);
297}
298
Shawn Willdend0772312014-09-18 12:27:57 -0600299class NewKeyGeneration : public KeymasterTest {
300 protected:
301 NewKeyGeneration() {
Shawn Willden2079ae82015-01-22 13:42:31 -0700302 params_.Reinitialize(key_generation_base_params, array_length(key_generation_base_params));
Shawn Willdend0772312014-09-18 12:27:57 -0600303 }
304
Shawn Willden2079ae82015-01-22 13:42:31 -0700305 void CheckBaseParams(const AuthorizationSet& auths) {
306 EXPECT_TRUE(contains(auths, TAG_PURPOSE, KM_PURPOSE_SIGN));
307 EXPECT_TRUE(contains(auths, TAG_PURPOSE, KM_PURPOSE_VERIFY));
308 EXPECT_TRUE(contains(auths, TAG_USER_ID, 7));
309 EXPECT_TRUE(contains(auths, TAG_USER_AUTH_ID, 8));
310 EXPECT_TRUE(contains(auths, TAG_AUTH_TIMEOUT, 300));
Shawn Willdend0772312014-09-18 12:27:57 -0600311
312 // Verify that App ID, App data and ROT are NOT included.
Shawn Willden2079ae82015-01-22 13:42:31 -0700313 EXPECT_FALSE(contains(auths, TAG_ROOT_OF_TRUST));
314 EXPECT_FALSE(contains(auths, TAG_APPLICATION_ID));
315 EXPECT_FALSE(contains(auths, TAG_APPLICATION_DATA));
Shawn Willdend0772312014-09-18 12:27:57 -0600316
317 // Just for giggles, check that some unexpected tags/values are NOT present.
Shawn Willden2079ae82015-01-22 13:42:31 -0700318 EXPECT_FALSE(contains(auths, TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
319 EXPECT_FALSE(contains(auths, TAG_PURPOSE, KM_PURPOSE_DECRYPT));
320 EXPECT_FALSE(contains(auths, TAG_AUTH_TIMEOUT, 301));
Shawn Willdend0772312014-09-18 12:27:57 -0600321
322 // Now check that unspecified, defaulted tags are correct.
Shawn Willden2079ae82015-01-22 13:42:31 -0700323 EXPECT_TRUE(contains(auths, TAG_ORIGIN, KM_ORIGIN_SOFTWARE));
324 EXPECT_TRUE(contains(auths, KM_TAG_CREATION_DATETIME));
Shawn Willdend0772312014-09-18 12:27:57 -0600325 }
Shawn Willdend0772312014-09-18 12:27:57 -0600326};
327
Shawn Willden2079ae82015-01-22 13:42:31 -0700328struct ParamListDelete {
329 void operator()(keymaster_key_param_set_t* p) { keymaster_free_param_set(p); }
330};
331
332typedef UniquePtr<keymaster_key_param_set_t, ParamListDelete> UniqueParamSetPtr;
333
Shawn Willden128ffe02014-08-06 12:31:33 -0600334TEST_F(NewKeyGeneration, Rsa) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700335 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA));
336 params_.push_back(Authorization(TAG_KEY_SIZE, 256));
337 params_.push_back(Authorization(TAG_RSA_PUBLIC_EXPONENT, 3));
338 ASSERT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
339 &characteristics_));
340 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
341 AuthorizationSet auths(characteristics_->sw_enforced);
342 CheckBaseParams(auths);
Shawn Willden128ffe02014-08-06 12:31:33 -0600343
Shawn Willden2079ae82015-01-22 13:42:31 -0700344 // Check specified tags are all present in auths
345 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_RSA));
346 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 256));
347 EXPECT_TRUE(contains(auths, TAG_RSA_PUBLIC_EXPONENT, 3));
Shawn Willden128ffe02014-08-06 12:31:33 -0600348}
349
Shawn Willden6bbe6782014-09-18 11:26:15 -0600350TEST_F(NewKeyGeneration, RsaDefaultSize) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700351 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA));
352 ASSERT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
353 &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600354
Shawn Willden2079ae82015-01-22 13:42:31 -0700355 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
356 AuthorizationSet auths(characteristics_->sw_enforced);
357 CheckBaseParams(auths);
Shawn Willden6bbe6782014-09-18 11:26:15 -0600358
Shawn Willden2079ae82015-01-22 13:42:31 -0700359 // Check specified tags are all present in auths
360 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_RSA));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600361
362 // Now check that unspecified, defaulted tags are correct.
Shawn Willden2079ae82015-01-22 13:42:31 -0700363 EXPECT_TRUE(contains(auths, TAG_RSA_PUBLIC_EXPONENT, 65537));
364 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 2048));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600365}
366
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600367TEST_F(NewKeyGeneration, Ecdsa) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700368 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
369 params_.push_back(Authorization(TAG_KEY_SIZE, 224));
370 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
371 &characteristics_));
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600372
Shawn Willden2079ae82015-01-22 13:42:31 -0700373 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
374 AuthorizationSet auths(characteristics_->sw_enforced);
375 CheckBaseParams(auths);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600376
Shawn Willden2079ae82015-01-22 13:42:31 -0700377 // Check specified tags are all present in auths characteristics
378 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
379 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 224));
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600380}
381
Shawn Willden6bbe6782014-09-18 11:26:15 -0600382TEST_F(NewKeyGeneration, EcdsaDefaultSize) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700383 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
384 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
385 &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600386
Shawn Willden2079ae82015-01-22 13:42:31 -0700387 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
388 AuthorizationSet auths(characteristics_->sw_enforced);
389 CheckBaseParams(auths);
Shawn Willden6bbe6782014-09-18 11:26:15 -0600390
Shawn Willden2079ae82015-01-22 13:42:31 -0700391 // Check specified tags are all present in auths
392 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600393
394 // Now check that unspecified, defaulted tags are correct.
Shawn Willden2079ae82015-01-22 13:42:31 -0700395 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 224));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600396}
397
398TEST_F(NewKeyGeneration, EcdsaInvalidSize) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700399 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
400 params_.push_back(Authorization(TAG_KEY_SIZE, 190));
401 EXPECT_EQ(KM_ERROR_UNSUPPORTED_KEY_SIZE,
402 device()->generate_key(device(), params_.data(), params_.size(), &blob_,
403 &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600404}
405
406TEST_F(NewKeyGeneration, EcdsaAllValidSizes) {
Shawn Willden8c856c82014-09-26 09:34:36 -0600407 size_t valid_sizes[] = {224, 256, 384, 521};
Shawn Willden6bbe6782014-09-18 11:26:15 -0600408 for (size_t size : valid_sizes) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700409 params_.Reinitialize(key_generation_base_params, array_length(key_generation_base_params));
410 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
411 params_.push_back(Authorization(TAG_KEY_SIZE, size));
412 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(),
413 &blob_, &characteristics_))
414 << "Failed to generate size: " << size;
415
416 FreeCharacteristics();
417 FreeKeyBlob();
Shawn Willden6bbe6782014-09-18 11:26:15 -0600418 }
419}
420
Shawn Willden19fca882015-01-22 16:35:30 -0700421TEST_F(NewKeyGeneration, AesOcb) {
422 keymaster_key_param_t params[] = {
423 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
424 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
425 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_KEY_SIZE, 128),
426 Authorization(TAG_BLOCK_MODE, KM_MODE_OCB), Authorization(TAG_CHUNK_LENGTH, 4096),
Shawn Willden7efb8782014-12-11 14:07:44 -0700427 Authorization(TAG_MAC_LENGTH, 16), Authorization(TAG_PADDING, KM_PAD_NONE),
Shawn Willden19fca882015-01-22 16:35:30 -0700428 };
Shawn Willden2079ae82015-01-22 13:42:31 -0700429 params_.Reinitialize(params, array_length(params));
430 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
431 &characteristics_));
Shawn Willden19fca882015-01-22 16:35:30 -0700432}
433
434TEST_F(NewKeyGeneration, AesOcbInvalidKeySize) {
435 keymaster_key_param_t params[] = {
436 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
437 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
438 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_KEY_SIZE, 129),
439 Authorization(TAG_BLOCK_MODE, KM_MODE_OCB), Authorization(TAG_CHUNK_LENGTH, 4096),
Shawn Willden7efb8782014-12-11 14:07:44 -0700440 Authorization(TAG_MAC_LENGTH, 16), Authorization(TAG_PADDING, KM_PAD_NONE),
Shawn Willden19fca882015-01-22 16:35:30 -0700441 };
Shawn Willden2079ae82015-01-22 13:42:31 -0700442 params_.Reinitialize(params, array_length(params));
443 EXPECT_EQ(KM_ERROR_UNSUPPORTED_KEY_SIZE,
444 device()->generate_key(device(), params_.data(), params_.size(), &blob_,
445 &characteristics_));
Shawn Willden19fca882015-01-22 16:35:30 -0700446}
447
448TEST_F(NewKeyGeneration, AesOcbAllValidSizes) {
449 keymaster_key_param_t params[] = {
450 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
451 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
Shawn Willden7efb8782014-12-11 14:07:44 -0700452 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_BLOCK_MODE, KM_MODE_OCB),
453 Authorization(TAG_MAC_LENGTH, 16), Authorization(TAG_CHUNK_LENGTH, 4096),
Shawn Willden19fca882015-01-22 16:35:30 -0700454 Authorization(TAG_PADDING, KM_PAD_NONE),
455 };
456
457 size_t valid_sizes[] = {128, 192, 256};
458 for (size_t size : valid_sizes) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700459 params_.Reinitialize(params, array_length(params));
460 params_.push_back(Authorization(TAG_KEY_SIZE, size));
461 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(),
462 &blob_, &characteristics_))
463 << "Failed to generate size: " << size;
464
465 FreeCharacteristics();
466 FreeKeyBlob();
Shawn Willden19fca882015-01-22 16:35:30 -0700467 }
468}
469
470TEST_F(NewKeyGeneration, AesOcbNoChunkLength) {
471 keymaster_key_param_t params[] = {
472 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
473 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
474 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_KEY_SIZE, 128),
475 Authorization(TAG_BLOCK_MODE, KM_MODE_OCB), Authorization(TAG_PADDING, KM_PAD_NONE),
476 };
Shawn Willden2079ae82015-01-22 13:42:31 -0700477 params_.Reinitialize(params, array_length(params));
478 EXPECT_EQ(KM_ERROR_INVALID_ARGUMENT,
479 device()->generate_key(device(), params_.data(), params_.size(), &blob_,
480 &characteristics_));
Shawn Willden19fca882015-01-22 16:35:30 -0700481}
482
483TEST_F(NewKeyGeneration, AesEcbUnsupported) {
484 keymaster_key_param_t params[] = {
485 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
486 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
487 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_KEY_SIZE, 128),
488 Authorization(TAG_BLOCK_MODE, KM_MODE_ECB), Authorization(TAG_PADDING, KM_PAD_NONE),
489 };
Shawn Willden2079ae82015-01-22 13:42:31 -0700490 params_.Reinitialize(params, array_length(params));
491 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
492 device()->generate_key(device(), params_.data(), params_.size(), &blob_,
493 &characteristics_));
Shawn Willden19fca882015-01-22 16:35:30 -0700494}
495
496TEST_F(NewKeyGeneration, AesOcbPaddingUnsupported) {
497 keymaster_key_param_t params[] = {
498 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
499 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
500 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_KEY_SIZE, 128),
501 Authorization(TAG_BLOCK_MODE, KM_MODE_OCB), Authorization(TAG_CHUNK_LENGTH, 4096),
502 Authorization(TAG_PADDING, KM_PAD_ZERO),
503 };
Shawn Willden2079ae82015-01-22 13:42:31 -0700504 params_.Reinitialize(params, array_length(params));
505 EXPECT_EQ(KM_ERROR_UNSUPPORTED_PADDING_MODE,
506 device()->generate_key(device(), params_.data(), params_.size(), &blob_,
507 &characteristics_));
Shawn Willden19fca882015-01-22 16:35:30 -0700508}
509
Shawn Willden7efb8782014-12-11 14:07:44 -0700510TEST_F(NewKeyGeneration, AesOcbInvalidMacLength) {
511 keymaster_key_param_t params[] = {
512 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
513 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
514 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_KEY_SIZE, 128),
515 Authorization(TAG_BLOCK_MODE, KM_MODE_OCB), Authorization(TAG_CHUNK_LENGTH, 4096),
516 Authorization(TAG_MAC_LENGTH, 17), Authorization(TAG_PADDING, KM_PAD_NONE),
517 };
Shawn Willden2079ae82015-01-22 13:42:31 -0700518 params_.Reinitialize(params, array_length(params));
519 EXPECT_EQ(KM_ERROR_INVALID_ARGUMENT,
520 device()->generate_key(device(), params_.data(), params_.size(), &blob_,
521 &characteristics_));
Shawn Willden7efb8782014-12-11 14:07:44 -0700522}
523
Shawn Willden76364712014-08-11 17:48:04 -0600524typedef KeymasterTest GetKeyCharacteristics;
525TEST_F(GetKeyCharacteristics, SimpleRsa) {
526 keymaster_key_param_t params[] = {
Shawn Willden3809b932014-12-02 06:59:46 -0700527 Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN), Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY),
528 Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA), Authorization(TAG_KEY_SIZE, 256),
529 Authorization(TAG_USER_ID, 7), Authorization(TAG_USER_AUTH_ID, 8),
530 Authorization(TAG_APPLICATION_ID, "app_id", 6), Authorization(TAG_AUTH_TIMEOUT, 300),
Shawn Willden76364712014-08-11 17:48:04 -0600531 };
532
Shawn Willden2079ae82015-01-22 13:42:31 -0700533 ASSERT_EQ(KM_ERROR_OK, device()->generate_key(device(), params, array_length(params), &blob_,
534 &characteristics_));
535 AuthorizationSet original(characteristics_->sw_enforced);
536 FreeCharacteristics();
Shawn Willden76364712014-08-11 17:48:04 -0600537
Shawn Willden2079ae82015-01-22 13:42:31 -0700538 keymaster_blob_t client_id = {.data = reinterpret_cast<const uint8_t*>("app_id"),
539 .data_length = 6};
540 ASSERT_EQ(KM_ERROR_OK,
541 device()->get_key_characteristics(device(), &blob_, &client_id, NULL /* app_data */,
542 &characteristics_));
543 EXPECT_EQ(original, AuthorizationSet(characteristics_->sw_enforced));
Shawn Willden76364712014-08-11 17:48:04 -0600544}
545
Shawn Willden61644f32014-08-18 13:43:14 -0600546/**
547 * Test class that provides some infrastructure for generating keys and signing messages.
548 */
Shawn Willden1615f2e2014-08-13 10:37:40 -0600549class SigningOperationsTest : public KeymasterTest {
550 protected:
Shawn Willden2079ae82015-01-22 13:42:31 -0700551 SigningOperationsTest() : out_params_(NULL), output_(NULL), signature_(NULL) {}
552 ~SigningOperationsTest() {
553 // Clean up so (most) tests won't have to.
554 FreeOutput();
555 FreeSignature();
556 }
557
Shawn Willden61644f32014-08-18 13:43:14 -0600558 void GenerateKey(keymaster_algorithm_t algorithm, keymaster_digest_t digest,
559 keymaster_padding_t padding, uint32_t key_size) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700560 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN));
561 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY));
562 params_.push_back(Authorization(TAG_ALGORITHM, algorithm));
563 params_.push_back(Authorization(TAG_KEY_SIZE, key_size));
564 params_.push_back(Authorization(TAG_USER_ID, 7));
565 params_.push_back(Authorization(TAG_USER_AUTH_ID, 8));
566 params_.push_back(Authorization(TAG_APPLICATION_ID, "app_id", 6));
567 params_.push_back(Authorization(TAG_AUTH_TIMEOUT, 300));
Shawn Willden43e999e2014-08-13 13:29:50 -0600568 if (static_cast<int>(digest) != -1)
Shawn Willden2079ae82015-01-22 13:42:31 -0700569 params_.push_back(TAG_DIGEST, digest);
Shawn Willden43e999e2014-08-13 13:29:50 -0600570 if (static_cast<int>(padding) != -1)
Shawn Willden2079ae82015-01-22 13:42:31 -0700571 params_.push_back(TAG_PADDING, padding);
572
573 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(),
574 &blob_, &characteristics_));
Shawn Willden61644f32014-08-18 13:43:14 -0600575 }
Shawn Willden1615f2e2014-08-13 10:37:40 -0600576
Shawn Willden61644f32014-08-18 13:43:14 -0600577 void SignMessage(const void* message, size_t size) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700578 EXPECT_EQ(KM_ERROR_OK, device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
579 array_length(client_params_), &out_params_,
580 &out_params_count_, &op_handle_));
581
582 EXPECT_EQ(KM_ERROR_OK,
583 device()->update(device(), op_handle_, reinterpret_cast<const uint8_t*>(message),
584 size, &input_consumed_, &output_, &output_length_));
585 EXPECT_EQ(0, output_length_);
586 FreeOutput();
587 EXPECT_EQ(size, input_consumed_);
588
589 EXPECT_EQ(KM_ERROR_OK,
590 device()->finish(device(), op_handle_, NULL /* signature to verify */,
591 0 /* signature to verify length */, &signature_,
592 &signature_length_));
593 EXPECT_GT(signature_length_, 0);
Shawn Willden437fbd12014-08-20 11:59:49 -0600594 }
595
Shawn Willden2079ae82015-01-22 13:42:31 -0700596 void FreeOutput() {
597 free(out_params_);
598 out_params_ = NULL;
599 free(output_);
600 output_ = NULL;
Shawn Willden61644f32014-08-18 13:43:14 -0600601 }
602
Shawn Willden2079ae82015-01-22 13:42:31 -0700603 void FreeSignature() {
604 free(signature_);
605 signature_ = NULL;
Shawn Willdenf268d742014-08-19 15:36:26 -0600606 }
607
Shawn Willden2079ae82015-01-22 13:42:31 -0700608 void corrupt_key_blob() {
609 uint8_t* tmp = const_cast<uint8_t*>(blob_.key_material);
610 ++tmp[blob_.key_material_size / 2];
Shawn Willden1615f2e2014-08-13 10:37:40 -0600611 }
612
Shawn Willden2079ae82015-01-22 13:42:31 -0700613 keymaster_blob_t client_id_ = {.data = reinterpret_cast<const uint8_t*>("app_id"),
614 .data_length = 6};
615 keymaster_key_param_t client_params_[1] = {
616 Authorization(TAG_APPLICATION_ID, client_id_.data, client_id_.data_length)};
617 keymaster_key_param_t* out_params_;
618 size_t out_params_count_;
619 uint64_t op_handle_;
620 size_t input_consumed_;
621 uint8_t* output_;
622 size_t output_length_;
623 uint8_t* signature_;
624 size_t signature_length_;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600625};
626
627TEST_F(SigningOperationsTest, RsaSuccess) {
Shawn Willden61644f32014-08-18 13:43:14 -0600628 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
Shawn Willdenffd790c2014-08-18 21:20:06 -0600629 const char message[] = "12345678901234567890123456789012";
Shawn Willdend05cba52014-09-26 09:58:12 -0600630 SignMessage(message, array_size(message) - 1);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600631}
632
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600633TEST_F(SigningOperationsTest, EcdsaSuccess) {
Shawn Willden8c856c82014-09-26 09:34:36 -0600634 GenerateKey(KM_ALGORITHM_ECDSA, KM_DIGEST_NONE, KM_PAD_NONE, 224 /* key size */);
Shawn Willdend05cba52014-09-26 09:58:12 -0600635 const char message[] = "123456789012345678901234567890123456789012345678";
636 SignMessage(message, array_size(message) - 1);
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600637}
638
Shawn Willden1615f2e2014-08-13 10:37:40 -0600639TEST_F(SigningOperationsTest, RsaAbort) {
Shawn Willden61644f32014-08-18 13:43:14 -0600640 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
Shawn Willden2079ae82015-01-22 13:42:31 -0700641 ASSERT_EQ(KM_ERROR_OK, device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
642 array_length(client_params_), &out_params_,
643 &out_params_count_, &op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600644
Shawn Willden2079ae82015-01-22 13:42:31 -0700645 EXPECT_EQ(KM_ERROR_OK, device()->abort(device(), op_handle_));
646 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600647}
648
649TEST_F(SigningOperationsTest, RsaUnsupportedDigest) {
Shawn Willden61644f32014-08-18 13:43:14 -0600650 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_SHA_2_256, KM_PAD_NONE, 256 /* key size */);
Shawn Willden2079ae82015-01-22 13:42:31 -0700651 ASSERT_EQ(KM_ERROR_UNSUPPORTED_DIGEST,
652 device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
653 array_length(client_params_), &out_params_, &out_params_count_,
654 &op_handle_));
655 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600656}
657
658TEST_F(SigningOperationsTest, RsaUnsupportedPadding) {
Shawn Willden61644f32014-08-18 13:43:14 -0600659 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_RSA_OAEP, 256 /* key size */);
Shawn Willden2079ae82015-01-22 13:42:31 -0700660 ASSERT_EQ(KM_ERROR_UNSUPPORTED_PADDING_MODE,
661 device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
662 array_length(client_params_), &out_params_, &out_params_count_,
663 &op_handle_));
664 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600665}
666
667TEST_F(SigningOperationsTest, RsaNoDigest) {
Shawn Willden61644f32014-08-18 13:43:14 -0600668 GenerateKey(KM_ALGORITHM_RSA, static_cast<keymaster_digest_t>(-1), KM_PAD_NONE,
669 256 /* key size */);
Shawn Willden2079ae82015-01-22 13:42:31 -0700670 ASSERT_EQ(KM_ERROR_UNSUPPORTED_DIGEST,
671 device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
672 array_length(client_params_), &out_params_, &out_params_count_,
673 &op_handle_));
674 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600675}
676
677TEST_F(SigningOperationsTest, RsaNoPadding) {
Shawn Willden61644f32014-08-18 13:43:14 -0600678 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, static_cast<keymaster_padding_t>(-1),
679 256 /* key size */);
Shawn Willden2079ae82015-01-22 13:42:31 -0700680 ASSERT_EQ(KM_ERROR_UNSUPPORTED_PADDING_MODE,
681 device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
682 array_length(client_params_), &out_params_, &out_params_count_,
683 &op_handle_));
684 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600685}
686
687TEST_F(SigningOperationsTest, RsaTooShortMessage) {
Shawn Willden61644f32014-08-18 13:43:14 -0600688 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
Shawn Willden2079ae82015-01-22 13:42:31 -0700689 ASSERT_EQ(KM_ERROR_OK, device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
690 array_length(client_params_), &out_params_,
691 &out_params_count_, &op_handle_));
692 ASSERT_EQ(KM_ERROR_OK,
693 device()->update(device(), op_handle_,
694 reinterpret_cast<const uint8_t*>("01234567890123456789012345678901"),
695 31, &input_consumed_, &output_, &output_length_));
696 EXPECT_EQ(0U, output_length_);
697 EXPECT_EQ(31U, input_consumed_);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600698
Shawn Willden2079ae82015-01-22 13:42:31 -0700699 ASSERT_EQ(KM_ERROR_UNKNOWN_ERROR,
700 device()->finish(device(), op_handle_, NULL, 0, &signature_, &signature_length_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600701
Shawn Willden2079ae82015-01-22 13:42:31 -0700702 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden43e999e2014-08-13 13:29:50 -0600703}
704
Shawn Willdend05cba52014-09-26 09:58:12 -0600705class VerificationOperationsTest : public SigningOperationsTest {
706 protected:
707 void VerifyMessage(const void* message, size_t message_len) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700708 EXPECT_TRUE(signature_ != NULL);
Shawn Willdend05cba52014-09-26 09:58:12 -0600709
Shawn Willden2079ae82015-01-22 13:42:31 -0700710 EXPECT_EQ(KM_ERROR_OK, device()->begin(device(), KM_PURPOSE_VERIFY, &blob_, client_params_,
711 array_length(client_params_), &out_params_,
712 &out_params_count_, &op_handle_));
713 ASSERT_EQ(KM_ERROR_OK,
714 device()->update(device(), op_handle_, reinterpret_cast<const uint8_t*>(message),
715 message_len, &input_consumed_, &output_, &output_length_));
716 EXPECT_EQ(0U, output_length_);
717 FreeOutput();
718 EXPECT_EQ(message_len, input_consumed_);
Shawn Willdend05cba52014-09-26 09:58:12 -0600719
Shawn Willden2079ae82015-01-22 13:42:31 -0700720 ASSERT_EQ(KM_ERROR_OK, device()->finish(device(), op_handle_, signature_, signature_length_,
721 &output_, &output_length_));
722 EXPECT_EQ(0U, output_length_);
Shawn Willdend05cba52014-09-26 09:58:12 -0600723
Shawn Willden2079ae82015-01-22 13:42:31 -0700724 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willdend05cba52014-09-26 09:58:12 -0600725 }
726};
727
Shawn Willden43e999e2014-08-13 13:29:50 -0600728TEST_F(VerificationOperationsTest, RsaSuccess) {
Shawn Willden61644f32014-08-18 13:43:14 -0600729 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
730 const char message[] = "12345678901234567890123456789012";
731 SignMessage(message, array_size(message) - 1);
Shawn Willdend05cba52014-09-26 09:58:12 -0600732 VerifyMessage(message, array_size(message) - 1);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600733}
734
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600735TEST_F(VerificationOperationsTest, EcdsaSuccess) {
Shawn Willden8c856c82014-09-26 09:34:36 -0600736 GenerateKey(KM_ALGORITHM_ECDSA, KM_DIGEST_NONE, KM_PAD_NONE, 224 /* key size */);
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600737 const char message[] = "123456789012345678901234567890123456789012345678";
738 SignMessage(message, array_size(message) - 1);
Shawn Willdend05cba52014-09-26 09:58:12 -0600739 VerifyMessage(message, array_size(message) - 1);
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600740}
741
Shawn Willden2079ae82015-01-22 13:42:31 -0700742typedef VerificationOperationsTest ExportKeyTest;
Shawn Willdenffd790c2014-08-18 21:20:06 -0600743TEST_F(ExportKeyTest, RsaSuccess) {
744 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
Shawn Willdenffd790c2014-08-18 21:20:06 -0600745
Shawn Willden2079ae82015-01-22 13:42:31 -0700746 uint8_t* export_data;
747 size_t export_data_length;
748 ASSERT_EQ(KM_ERROR_OK,
749 device()->export_key(device(), KM_KEY_FORMAT_X509, &blob_, &client_id_,
750 NULL /* app_data */, &export_data, &export_data_length));
751 EXPECT_TRUE(export_data != NULL);
752 EXPECT_GT(export_data_length, 0);
Shawn Willdene46a43f2014-08-27 10:35:36 -0600753
754 // TODO(swillden): Verify that the exported key is actually usable to verify signatures.
Shawn Willden2079ae82015-01-22 13:42:31 -0700755 free(export_data);
Shawn Willdenffd790c2014-08-18 21:20:06 -0600756}
757
Shawn Willdenf268d742014-08-19 15:36:26 -0600758TEST_F(ExportKeyTest, EcdsaSuccess) {
Shawn Willden8c856c82014-09-26 09:34:36 -0600759 GenerateKey(KM_ALGORITHM_ECDSA, KM_DIGEST_NONE, KM_PAD_NONE, 224 /* key size */);
Shawn Willdenf268d742014-08-19 15:36:26 -0600760
Shawn Willden2079ae82015-01-22 13:42:31 -0700761 uint8_t* export_data;
762 size_t export_data_length;
763 ASSERT_EQ(KM_ERROR_OK,
764 device()->export_key(device(), KM_KEY_FORMAT_X509, &blob_, &client_id_,
765 NULL /* app_data */, &export_data, &export_data_length));
766 EXPECT_TRUE(export_data != NULL);
767 EXPECT_GT(export_data_length, 0);
Shawn Willdene46a43f2014-08-27 10:35:36 -0600768
769 // TODO(swillden): Verify that the exported key is actually usable to verify signatures.
Shawn Willden2079ae82015-01-22 13:42:31 -0700770 free(export_data);
Shawn Willdenf268d742014-08-19 15:36:26 -0600771}
772
773TEST_F(ExportKeyTest, RsaUnsupportedKeyFormat) {
774 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256);
775
Shawn Willden2079ae82015-01-22 13:42:31 -0700776 uint8_t dummy[] = {1};
777 uint8_t* export_data = dummy; // So it's not NULL;
778 size_t export_data_length;
779 ASSERT_EQ(KM_ERROR_UNSUPPORTED_KEY_FORMAT,
780 device()->export_key(device(), KM_KEY_FORMAT_PKCS8, &blob_, &client_id_,
781 NULL /* app_data */, &export_data, &export_data_length));
782 ASSERT_TRUE(export_data == NULL);
Shawn Willdenf268d742014-08-19 15:36:26 -0600783}
784
785TEST_F(ExportKeyTest, RsaCorruptedKeyBlob) {
786 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256);
Shawn Willden2079ae82015-01-22 13:42:31 -0700787 corrupt_key_blob();
Shawn Willdenf268d742014-08-19 15:36:26 -0600788
Shawn Willden2079ae82015-01-22 13:42:31 -0700789 uint8_t dummy[] = {1};
790 uint8_t* export_data = dummy; // So it's not NULL
791 size_t export_data_length;
792 ASSERT_EQ(KM_ERROR_INVALID_KEY_BLOB,
793 device()->export_key(device(), KM_KEY_FORMAT_X509, &blob_, &client_id_,
794 NULL /* app_data */, &export_data, &export_data_length));
795 ASSERT_TRUE(export_data == NULL);
Shawn Willdenf268d742014-08-19 15:36:26 -0600796}
797
Shawn Willden437fbd12014-08-20 11:59:49 -0600798static string read_file(const string& file_name) {
799 ifstream file_stream(file_name, std::ios::binary);
800 istreambuf_iterator<char> file_begin(file_stream);
801 istreambuf_iterator<char> file_end;
802 return string(file_begin, file_end);
803}
804
Shawn Willden2079ae82015-01-22 13:42:31 -0700805class ImportKeyTest : public VerificationOperationsTest {
806 protected:
807 ImportKeyTest() {
808 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN));
809 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY));
810 params_.push_back(Authorization(TAG_DIGEST, KM_DIGEST_NONE));
811 params_.push_back(Authorization(TAG_PADDING, KM_PAD_NONE));
812 params_.push_back(Authorization(TAG_USER_ID, 7));
813 params_.push_back(Authorization(TAG_USER_AUTH_ID, 8));
814 params_.push_back(Authorization(TAG_APPLICATION_ID, "app_id", 6));
815 params_.push_back(Authorization(TAG_AUTH_TIMEOUT, 300));
816 }
817};
Shawn Willden437fbd12014-08-20 11:59:49 -0600818
Shawn Willden2079ae82015-01-22 13:42:31 -0700819TEST_F(ImportKeyTest, RsaSuccess) {
Shawn Willden81effc62014-08-27 10:08:46 -0600820 string pk8_key = read_file("rsa_privkey_pk8.der");
Shawn Willden437fbd12014-08-20 11:59:49 -0600821 ASSERT_EQ(633U, pk8_key.size());
822
Shawn Willden2079ae82015-01-22 13:42:31 -0700823 ASSERT_EQ(KM_ERROR_OK,
824 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
825 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
826 &blob_, &characteristics_));
827 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
828 AuthorizationSet auths(characteristics_->sw_enforced);
Shawn Willden437fbd12014-08-20 11:59:49 -0600829
830 // Check values derived from the key.
Shawn Willden2079ae82015-01-22 13:42:31 -0700831 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_RSA));
832 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 1024));
833 EXPECT_TRUE(contains(auths, TAG_RSA_PUBLIC_EXPONENT, 65537U));
Shawn Willden437fbd12014-08-20 11:59:49 -0600834
835 // And values provided by GoogleKeymaster
Shawn Willden2079ae82015-01-22 13:42:31 -0700836 EXPECT_TRUE(contains(auths, TAG_ORIGIN, KM_ORIGIN_IMPORTED));
837 EXPECT_TRUE(contains(auths, KM_TAG_CREATION_DATETIME));
Shawn Willden437fbd12014-08-20 11:59:49 -0600838
839 size_t message_len = 1024 / 8;
840 UniquePtr<uint8_t[]> message(new uint8_t[message_len]);
841 std::fill(message.get(), message.get() + message_len, 'a');
Shawn Willden2079ae82015-01-22 13:42:31 -0700842 SignMessage(message.get(), message_len);
843 VerifyMessage(message.get(), message_len);
Shawn Willden437fbd12014-08-20 11:59:49 -0600844}
845
Shawn Willden6bbe6782014-09-18 11:26:15 -0600846TEST_F(ImportKeyTest, RsaKeySizeMismatch) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700847 params_.push_back(Authorization(TAG_KEY_SIZE, 2048)); // Doesn't match key
Shawn Willden6bbe6782014-09-18 11:26:15 -0600848
849 string pk8_key = read_file("rsa_privkey_pk8.der");
850 ASSERT_EQ(633U, pk8_key.size());
851
Shawn Willden2079ae82015-01-22 13:42:31 -0700852 ASSERT_EQ(KM_ERROR_IMPORT_PARAMETER_MISMATCH,
853 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
854 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
855 &blob_, &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600856}
857
858TEST_F(ImportKeyTest, RsaPublicExponenMismatch) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700859 params_.push_back(Authorization(TAG_RSA_PUBLIC_EXPONENT, 3)); // Doesn't match key
Shawn Willden6bbe6782014-09-18 11:26:15 -0600860
861 string pk8_key = read_file("rsa_privkey_pk8.der");
862 ASSERT_EQ(633U, pk8_key.size());
863
Shawn Willden2079ae82015-01-22 13:42:31 -0700864 ASSERT_EQ(KM_ERROR_IMPORT_PARAMETER_MISMATCH,
865 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
866 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
867 &blob_, &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600868}
869
Shawn Willden81effc62014-08-27 10:08:46 -0600870TEST_F(ImportKeyTest, EcdsaSuccess) {
Shawn Willden81effc62014-08-27 10:08:46 -0600871 string pk8_key = read_file("ec_privkey_pk8.der");
872 ASSERT_EQ(138U, pk8_key.size());
873
Shawn Willden2079ae82015-01-22 13:42:31 -0700874 ASSERT_EQ(KM_ERROR_OK,
875 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
876 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
877 &blob_, &characteristics_));
878 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
879 AuthorizationSet auths(characteristics_->sw_enforced);
Shawn Willden81effc62014-08-27 10:08:46 -0600880
881 // Check values derived from the key.
Shawn Willden2079ae82015-01-22 13:42:31 -0700882 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
883 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 256));
Shawn Willden81effc62014-08-27 10:08:46 -0600884
885 // And values provided by GoogleKeymaster
Shawn Willden2079ae82015-01-22 13:42:31 -0700886 EXPECT_TRUE(contains(auths, TAG_ORIGIN, KM_ORIGIN_IMPORTED));
887 EXPECT_TRUE(contains(auths, KM_TAG_CREATION_DATETIME));
Shawn Willden81effc62014-08-27 10:08:46 -0600888
Shawn Willden2079ae82015-01-22 13:42:31 -0700889 size_t message_len = 1024;
Shawn Willden81effc62014-08-27 10:08:46 -0600890 UniquePtr<uint8_t[]> message(new uint8_t[message_len]);
891 std::fill(message.get(), message.get() + message_len, 'a');
Shawn Willden2079ae82015-01-22 13:42:31 -0700892 SignMessage(message.get(), message_len);
893 VerifyMessage(message.get(), message_len);
Shawn Willden81effc62014-08-27 10:08:46 -0600894}
895
Shawn Willden2079ae82015-01-22 13:42:31 -0700896TEST_F(ImportKeyTest, EcdsaKeySizeMismatch) {
897 params_.push_back(Authorization(TAG_KEY_SIZE, 224)); // Doesn't match key
Shawn Willden6bbe6782014-09-18 11:26:15 -0600898
Shawn Willden2079ae82015-01-22 13:42:31 -0700899 string pk8_key = read_file("rsa_privkey_pk8.der");
900 ASSERT_EQ(633U, pk8_key.size());
Shawn Willden6bbe6782014-09-18 11:26:15 -0600901
Shawn Willden2079ae82015-01-22 13:42:31 -0700902 ASSERT_EQ(KM_ERROR_IMPORT_PARAMETER_MISMATCH,
903 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
904 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
905 &blob_, &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600906}
907
Shawn Willden2665e862014-11-24 14:46:21 -0700908typedef KeymasterTest VersionTest;
909TEST_F(VersionTest, GetVersion) {
910 GetVersionRequest req;
911 GetVersionResponse rsp;
Shawn Willden2079ae82015-01-22 13:42:31 -0700912 device_.GetVersion(req, &rsp);
Shawn Willden2665e862014-11-24 14:46:21 -0700913 EXPECT_EQ(KM_ERROR_OK, rsp.error);
914 EXPECT_EQ(1, rsp.major_ver);
915 EXPECT_EQ(0, rsp.minor_ver);
916 EXPECT_EQ(0, rsp.subminor_ver);
917}
918
Shawn Willden4200f212014-12-02 07:01:21 -0700919/**
920 * Test class that provides some infrastructure for generating keys and encrypting messages.
921 */
922class EncryptionOperationsTest : public KeymasterTest {
923 protected:
924 void GenerateKey(keymaster_algorithm_t algorithm, keymaster_padding_t padding,
925 uint32_t key_size) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700926 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
927 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT));
928 params_.push_back(Authorization(TAG_ALGORITHM, algorithm));
929 params_.push_back(Authorization(TAG_KEY_SIZE, key_size));
930 params_.push_back(Authorization(TAG_USER_ID, 7));
931 params_.push_back(Authorization(TAG_USER_AUTH_ID, 8));
932 params_.push_back(Authorization(TAG_APPLICATION_ID, "app_id", 6));
933 params_.push_back(Authorization(TAG_AUTH_TIMEOUT, 300));
Shawn Willden4200f212014-12-02 07:01:21 -0700934 if (static_cast<int>(padding) != -1)
Shawn Willden2079ae82015-01-22 13:42:31 -0700935 params_.push_back(TAG_PADDING, padding);
936 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(),
937 &blob_, &characteristics_));
Shawn Willden4200f212014-12-02 07:01:21 -0700938 }
939
Shawn Willden907c3012014-12-08 15:51:55 -0700940 void GenerateSymmetricKey(keymaster_algorithm_t algorithm, uint32_t key_size,
941 keymaster_block_mode_t block_mode, uint32_t chunk_length) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700942 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
943 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT));
944 params_.push_back(Authorization(TAG_ALGORITHM, algorithm));
945 params_.push_back(Authorization(TAG_BLOCK_MODE, block_mode));
946 params_.push_back(Authorization(TAG_CHUNK_LENGTH, chunk_length));
947 params_.push_back(Authorization(TAG_KEY_SIZE, key_size));
948 params_.push_back(Authorization(TAG_MAC_LENGTH, 16));
949 params_.push_back(Authorization(TAG_USER_ID, 7));
950 params_.push_back(Authorization(TAG_USER_AUTH_ID, 8));
951 params_.push_back(Authorization(TAG_APPLICATION_ID, "app_id", 6));
952 params_.push_back(Authorization(TAG_AUTH_TIMEOUT, 300));
953
954 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(),
955 &blob_, &characteristics_));
Shawn Willden907c3012014-12-08 15:51:55 -0700956 }
957
Shawn Willden4200f212014-12-02 07:01:21 -0700958 keymaster_error_t BeginOperation(keymaster_purpose_t purpose,
959 const keymaster_key_blob_t& key_blob, uint64_t* op_handle) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700960 return device()->begin(device(), purpose, &key_blob, client_params_,
961 array_length(client_params_), &out_params_, &out_params_count_,
962 op_handle);
Shawn Willden4200f212014-12-02 07:01:21 -0700963 }
964
965 keymaster_error_t UpdateOperation(uint64_t op_handle, const void* message, size_t size,
Shawn Willdenb7361132014-12-08 08:15:14 -0700966 string* output, size_t* input_consumed) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700967 uint8_t* out_tmp = NULL;
968 size_t out_length;
969 keymaster_error_t error =
970 device()->update(device(), op_handle, reinterpret_cast<const uint8_t*>(message), size,
971 input_consumed, &out_tmp, &out_length);
972 if (out_tmp)
973 *output = string(reinterpret_cast<char*>(out_tmp), out_length);
974 free(out_tmp);
975 return error;
Shawn Willden4200f212014-12-02 07:01:21 -0700976 }
977
978 keymaster_error_t FinishOperation(uint64_t op_handle, string* output) {
Shawn Willden2079ae82015-01-22 13:42:31 -0700979 uint8_t* out_tmp = NULL;
980 size_t out_length;
981 keymaster_error_t error = device()->finish(device(), op_handle, NULL /* signature */,
982 0 /* signature_length */, &out_tmp, &out_length);
983 if (out_tmp)
984 *output = string(reinterpret_cast<char*>(out_tmp), out_length);
985 free(out_tmp);
986 return error;
Shawn Willden4200f212014-12-02 07:01:21 -0700987 }
988
989 string ProcessMessage(keymaster_purpose_t purpose, const keymaster_key_blob_t& key_blob,
990 const void* message, size_t size) {
991 uint64_t op_handle;
992 EXPECT_EQ(KM_ERROR_OK, BeginOperation(purpose, key_blob, &op_handle));
993
994 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -0700995 size_t input_consumed;
996 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, message, size, &result, &input_consumed));
997 EXPECT_EQ(size, input_consumed);
Shawn Willden4200f212014-12-02 07:01:21 -0700998 EXPECT_EQ(KM_ERROR_OK, FinishOperation(op_handle, &result));
Shawn Willdenb7361132014-12-08 08:15:14 -0700999
Shawn Willden4200f212014-12-02 07:01:21 -07001000 return result;
1001 }
1002
1003 string EncryptMessage(const void* message, size_t size) {
Shawn Willden2079ae82015-01-22 13:42:31 -07001004 return ProcessMessage(KM_PURPOSE_ENCRYPT, blob_, message, size);
Shawn Willden4200f212014-12-02 07:01:21 -07001005 }
1006
1007 string DecryptMessage(const void* ciphertext, size_t size) {
Shawn Willden2079ae82015-01-22 13:42:31 -07001008 return ProcessMessage(KM_PURPOSE_DECRYPT, blob_, ciphertext, size);
Shawn Willden4200f212014-12-02 07:01:21 -07001009 }
1010
1011 void AddClientParams(AuthorizationSet* set) { set->push_back(TAG_APPLICATION_ID, "app_id", 6); }
1012
Shawn Willden2079ae82015-01-22 13:42:31 -07001013 const void corrupt_key_blob() {
1014 uint8_t* tmp = const_cast<uint8_t*>(blob_.key_material);
1015 ++tmp[blob_.key_material_size / 2];
Shawn Willden4200f212014-12-02 07:01:21 -07001016 }
1017
Shawn Willden2079ae82015-01-22 13:42:31 -07001018 keymaster_blob_t client_id_ = {.data = reinterpret_cast<const uint8_t*>("app_id"),
1019 .data_length = 6};
1020 keymaster_key_param_t client_params_[1] = {
1021 Authorization(TAG_APPLICATION_ID, client_id_.data, client_id_.data_length)};
1022
1023 keymaster_key_param_t* out_params_;
1024 size_t out_params_count_;
Shawn Willden4200f212014-12-02 07:01:21 -07001025};
1026
1027TEST_F(EncryptionOperationsTest, RsaOaepSuccess) {
1028 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_OAEP, 512);
1029 const char message[] = "Hello World!";
1030 string ciphertext1 = EncryptMessage(message, strlen(message));
1031 EXPECT_EQ(512 / 8, ciphertext1.size());
1032
1033 string ciphertext2 = EncryptMessage(message, strlen(message));
1034 EXPECT_EQ(512 / 8, ciphertext2.size());
1035
1036 // OAEP randomizes padding so every result should be different.
1037 EXPECT_NE(ciphertext1, ciphertext2);
1038}
1039
1040TEST_F(EncryptionOperationsTest, RsaOaepRoundTrip) {
1041 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_OAEP, 512);
1042 const char message[] = "Hello World!";
1043 string ciphertext = EncryptMessage(message, strlen(message));
1044 EXPECT_EQ(512 / 8, ciphertext.size());
1045
1046 string plaintext = DecryptMessage(ciphertext.data(), ciphertext.size());
1047 EXPECT_EQ(message, plaintext);
1048}
1049
1050TEST_F(EncryptionOperationsTest, RsaOaepTooLarge) {
1051 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_OAEP, 512);
1052 const char message[] = "12345678901234567890123";
1053 uint64_t op_handle;
1054 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -07001055 size_t input_consumed;
Shawn Willden4200f212014-12-02 07:01:21 -07001056
Shawn Willden2079ae82015-01-22 13:42:31 -07001057 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_ENCRYPT, blob_, &op_handle));
Shawn Willdenb7361132014-12-08 08:15:14 -07001058 EXPECT_EQ(KM_ERROR_OK,
1059 UpdateOperation(op_handle, message, array_size(message), &result, &input_consumed));
Shawn Willden4200f212014-12-02 07:01:21 -07001060 EXPECT_EQ(KM_ERROR_INVALID_INPUT_LENGTH, FinishOperation(op_handle, &result));
1061 EXPECT_EQ(0, result.size());
1062}
1063
1064TEST_F(EncryptionOperationsTest, RsaOaepCorruptedDecrypt) {
1065 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_OAEP, 512);
1066 const char message[] = "Hello World!";
1067 string ciphertext = EncryptMessage(message, strlen(message));
1068 EXPECT_EQ(512 / 8, ciphertext.size());
1069
1070 // Corrupt the ciphertext
1071 ciphertext[512 / 8 / 2]++;
1072
1073 uint64_t op_handle;
1074 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -07001075 size_t input_consumed;
Shawn Willden2079ae82015-01-22 13:42:31 -07001076 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_DECRYPT, blob_, &op_handle));
Shawn Willdenb7361132014-12-08 08:15:14 -07001077 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, ciphertext.data(), ciphertext.size(), &result,
1078 &input_consumed));
Shawn Willden4200f212014-12-02 07:01:21 -07001079 EXPECT_EQ(KM_ERROR_UNKNOWN_ERROR, FinishOperation(op_handle, &result));
1080 EXPECT_EQ(0, result.size());
1081}
1082
1083TEST_F(EncryptionOperationsTest, RsaPkcs1Success) {
1084 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_PKCS1_1_5_ENCRYPT, 512);
1085 const char message[] = "Hello World!";
1086 string ciphertext1 = EncryptMessage(message, strlen(message));
1087 EXPECT_EQ(512 / 8, ciphertext1.size());
1088
1089 string ciphertext2 = EncryptMessage(message, strlen(message));
1090 EXPECT_EQ(512 / 8, ciphertext2.size());
1091
1092 // PKCS1 v1.5 randomizes padding so every result should be different.
1093 EXPECT_NE(ciphertext1, ciphertext2);
1094}
1095
1096TEST_F(EncryptionOperationsTest, RsaPkcs1RoundTrip) {
1097 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_PKCS1_1_5_ENCRYPT, 512);
1098 const char message[] = "Hello World!";
1099 string ciphertext = EncryptMessage(message, strlen(message));
1100 EXPECT_EQ(512 / 8, ciphertext.size());
1101
1102 string plaintext = DecryptMessage(ciphertext.data(), ciphertext.size());
1103 EXPECT_EQ(message, plaintext);
1104}
1105
1106TEST_F(EncryptionOperationsTest, RsaPkcs1TooLarge) {
1107 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_PKCS1_1_5_ENCRYPT, 512);
1108 const char message[] = "1234567890123456789012345678901234567890123456789012";
1109 uint64_t op_handle;
1110 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -07001111 size_t input_consumed;
Shawn Willden4200f212014-12-02 07:01:21 -07001112
Shawn Willden2079ae82015-01-22 13:42:31 -07001113 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_ENCRYPT, blob_, &op_handle));
Shawn Willdenb7361132014-12-08 08:15:14 -07001114 EXPECT_EQ(KM_ERROR_OK,
1115 UpdateOperation(op_handle, message, array_size(message), &result, &input_consumed));
Shawn Willden4200f212014-12-02 07:01:21 -07001116 EXPECT_EQ(KM_ERROR_INVALID_INPUT_LENGTH, FinishOperation(op_handle, &result));
1117 EXPECT_EQ(0, result.size());
1118}
1119
1120TEST_F(EncryptionOperationsTest, RsaPkcs1CorruptedDecrypt) {
1121 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_PKCS1_1_5_ENCRYPT, 512);
1122 const char message[] = "Hello World!";
1123 string ciphertext = EncryptMessage(message, strlen(message));
1124 EXPECT_EQ(512 / 8, ciphertext.size());
1125
1126 // Corrupt the ciphertext
1127 ciphertext[512 / 8 / 2]++;
1128
1129 uint64_t op_handle;
1130 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -07001131 size_t input_consumed;
Shawn Willden2079ae82015-01-22 13:42:31 -07001132 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_DECRYPT, blob_, &op_handle));
Shawn Willdenb7361132014-12-08 08:15:14 -07001133 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, ciphertext.data(), ciphertext.size(), &result,
1134 &input_consumed));
Shawn Willden4200f212014-12-02 07:01:21 -07001135 EXPECT_EQ(KM_ERROR_UNKNOWN_ERROR, FinishOperation(op_handle, &result));
1136 EXPECT_EQ(0, result.size());
1137}
1138
Shawn Willden907c3012014-12-08 15:51:55 -07001139TEST_F(EncryptionOperationsTest, AesOcbSuccess) {
1140 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1141 const char message[] = "Hello World!";
1142 string ciphertext1 = EncryptMessage(message, strlen(message));
1143 EXPECT_EQ(12 /* nonce */ + strlen(message) + 16 /* tag */, ciphertext1.size());
1144
1145 string ciphertext2 = EncryptMessage(message, strlen(message));
1146 EXPECT_EQ(12 /* nonce */ + strlen(message) + 16 /* tag */, ciphertext2.size());
1147
1148 // OCB uses a random nonce, so every output should be different
1149 EXPECT_NE(ciphertext1, ciphertext2);
1150}
1151
Shawn Willden128ffe02014-08-06 12:31:33 -06001152} // namespace test
1153} // namespace keymaster