blob: bd3553c736ce1b11e4ce76c2a40830cad88d4db0 [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 Willden5b53c992015-02-02 08:05:25 -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 Willden5b53c992015-02-02 08:05:25 -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 Willden5b53c992015-02-02 08:05:25 -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 Willden5b53c992015-02-02 08:05:25 -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
Shawn Willden6dde87c2014-12-11 14:08:48 -0700102 const keymaster_key_blob_t& key_blob() { return blob_; }
103
Shawn Willden5b53c992015-02-02 08:05:25 -0700104 SoftKeymasterDevice device_;
105
106 AuthorizationSet params_;
107 keymaster_key_blob_t blob_;
108 keymaster_key_characteristics_t* characteristics_;
Shawn Willden128ffe02014-08-06 12:31:33 -0600109};
110
Shawn Willden128ffe02014-08-06 12:31:33 -0600111typedef KeymasterTest CheckSupported;
112TEST_F(CheckSupported, SupportedAlgorithms) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700113 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
114 device()->get_supported_algorithms(device(), NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600115
Shawn Willden5b53c992015-02-02 08:05:25 -0700116 size_t len;
117 keymaster_algorithm_t* algorithms;
118 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_algorithms(device(), &algorithms, &len));
119 ASSERT_EQ(4U, len);
120 EXPECT_EQ(KM_ALGORITHM_RSA, algorithms[0]);
121 EXPECT_EQ(KM_ALGORITHM_DSA, algorithms[1]);
122 EXPECT_EQ(KM_ALGORITHM_ECDSA, algorithms[2]);
123 EXPECT_EQ(KM_ALGORITHM_AES, algorithms[3]);
124
125 free(algorithms);
Shawn Willden128ffe02014-08-06 12:31:33 -0600126}
127
128TEST_F(CheckSupported, SupportedBlockModes) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700129 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
130 device()->get_supported_block_modes(device(), KM_ALGORITHM_RSA, KM_PURPOSE_ENCRYPT,
131 NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600132
Shawn Willden5b53c992015-02-02 08:05:25 -0700133 size_t len;
134 keymaster_block_mode_t* modes;
135 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
136 device()->get_supported_block_modes(device(), KM_ALGORITHM_RSA, KM_PURPOSE_ENCRYPT,
137 &modes, &len));
Shawn Willden128ffe02014-08-06 12:31:33 -0600138
Shawn Willden5b53c992015-02-02 08:05:25 -0700139 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
140 device()->get_supported_block_modes(device(), KM_ALGORITHM_DSA, KM_PURPOSE_ENCRYPT,
141 &modes, &len));
Shawn Willden28e41472014-08-18 13:35:22 -0600142
Shawn Willden5b53c992015-02-02 08:05:25 -0700143 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
144 device()->get_supported_block_modes(device(), KM_ALGORITHM_ECDSA, KM_PURPOSE_ENCRYPT,
145 &modes, &len));
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600146
Shawn Willden5b53c992015-02-02 08:05:25 -0700147 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
148 device()->get_supported_block_modes(device(), KM_ALGORITHM_AES, KM_PURPOSE_ENCRYPT,
149 &modes, &len));
Shawn Willden128ffe02014-08-06 12:31:33 -0600150}
151
152TEST_F(CheckSupported, SupportedPaddingModes) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700153 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
154 device()->get_supported_padding_modes(device(), KM_ALGORITHM_RSA, KM_PURPOSE_ENCRYPT,
155 NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600156
Shawn Willden5b53c992015-02-02 08:05:25 -0700157 size_t len;
158 keymaster_padding_t* modes;
159 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_padding_modes(device(), KM_ALGORITHM_RSA,
160 KM_PURPOSE_SIGN, &modes, &len));
161 ExpectContains(KM_PAD_NONE, modes, len);
162 free(modes);
Shawn Willden128ffe02014-08-06 12:31:33 -0600163
Shawn Willden5b53c992015-02-02 08:05:25 -0700164 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_padding_modes(device(), KM_ALGORITHM_DSA,
165 KM_PURPOSE_SIGN, &modes, &len));
166 ExpectContains(KM_PAD_NONE, modes, len);
167 free(modes);
Shawn Willden28e41472014-08-18 13:35:22 -0600168
Shawn Willden5b53c992015-02-02 08:05:25 -0700169 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_padding_modes(device(), KM_ALGORITHM_ECDSA,
170 KM_PURPOSE_SIGN, &modes, &len));
171 ExpectContains(KM_PAD_NONE, modes, len);
172 free(modes);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600173
Shawn Willden5b53c992015-02-02 08:05:25 -0700174 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_padding_modes(device(), KM_ALGORITHM_AES,
175 KM_PURPOSE_SIGN, &modes, &len));
176 EXPECT_EQ(0, len);
177 free(modes);
Shawn Willden128ffe02014-08-06 12:31:33 -0600178}
179
180TEST_F(CheckSupported, SupportedDigests) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700181 EXPECT_EQ(
182 KM_ERROR_OUTPUT_PARAMETER_NULL,
183 device()->get_supported_digests(device(), KM_ALGORITHM_RSA, KM_PURPOSE_SIGN, NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600184
Shawn Willden5b53c992015-02-02 08:05:25 -0700185 size_t len;
186 keymaster_digest_t* digests;
187 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_digests(device(), KM_ALGORITHM_RSA,
188 KM_PURPOSE_SIGN, &digests, &len));
189 ExpectContains(KM_DIGEST_NONE, digests, len);
190 free(digests);
Shawn Willden128ffe02014-08-06 12:31:33 -0600191
Shawn Willden5b53c992015-02-02 08:05:25 -0700192 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_digests(device(), KM_ALGORITHM_DSA,
193 KM_PURPOSE_SIGN, &digests, &len));
194 ExpectContains(KM_DIGEST_NONE, digests, len);
195 free(digests);
Shawn Willden28e41472014-08-18 13:35:22 -0600196
Shawn Willden5b53c992015-02-02 08:05:25 -0700197 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_digests(device(), KM_ALGORITHM_ECDSA,
198 KM_PURPOSE_SIGN, &digests, &len));
199 ExpectContains(KM_DIGEST_NONE, digests, len);
200 free(digests);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600201
Shawn Willden5b53c992015-02-02 08:05:25 -0700202 EXPECT_EQ(KM_ERROR_OK, device()->get_supported_digests(device(), KM_ALGORITHM_AES,
203 KM_PURPOSE_SIGN, &digests, &len));
204 EXPECT_EQ(0, len);
205 free(digests);
Shawn Willden128ffe02014-08-06 12:31:33 -0600206}
207
208TEST_F(CheckSupported, SupportedImportFormats) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700209 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
210 device()->get_supported_import_formats(device(), KM_ALGORITHM_RSA, NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600211
Shawn Willden5b53c992015-02-02 08:05:25 -0700212 size_t len;
213 keymaster_key_format_t* formats;
214 EXPECT_EQ(KM_ERROR_OK,
215 device()->get_supported_import_formats(device(), KM_ALGORITHM_RSA, &formats, &len));
216 ExpectContains(KM_KEY_FORMAT_PKCS8, formats, len);
217 free(formats);
Shawn Willden128ffe02014-08-06 12:31:33 -0600218
Shawn Willden5b53c992015-02-02 08:05:25 -0700219 EXPECT_EQ(KM_ERROR_OK,
220 device()->get_supported_import_formats(device(), KM_ALGORITHM_DSA, &formats, &len));
221 ExpectContains(KM_KEY_FORMAT_PKCS8, formats, len);
222 free(formats);
Shawn Willden28e41472014-08-18 13:35:22 -0600223
Shawn Willden5b53c992015-02-02 08:05:25 -0700224 EXPECT_EQ(KM_ERROR_OK,
225 device()->get_supported_import_formats(device(), KM_ALGORITHM_ECDSA, &formats, &len));
226 ExpectContains(KM_KEY_FORMAT_PKCS8, formats, len);
227 free(formats);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600228
Shawn Willden5b53c992015-02-02 08:05:25 -0700229 EXPECT_EQ(KM_ERROR_OK,
230 device()->get_supported_import_formats(device(), KM_ALGORITHM_AES, &formats, &len));
231 EXPECT_EQ(0, len);
232 free(formats);
Shawn Willden128ffe02014-08-06 12:31:33 -0600233}
234
235TEST_F(CheckSupported, SupportedExportFormats) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700236 EXPECT_EQ(KM_ERROR_OUTPUT_PARAMETER_NULL,
237 device()->get_supported_export_formats(device(), KM_ALGORITHM_RSA, NULL, NULL));
Shawn Willden128ffe02014-08-06 12:31:33 -0600238
Shawn Willden5b53c992015-02-02 08:05:25 -0700239 size_t len;
240 keymaster_key_format_t* formats;
241 EXPECT_EQ(KM_ERROR_OK,
242 device()->get_supported_export_formats(device(), KM_ALGORITHM_RSA, &formats, &len));
243 ExpectContains(KM_KEY_FORMAT_X509, formats, len);
244 free(formats);
Shawn Willden128ffe02014-08-06 12:31:33 -0600245
Shawn Willden5b53c992015-02-02 08:05:25 -0700246 EXPECT_EQ(KM_ERROR_OK,
247 device()->get_supported_export_formats(device(), KM_ALGORITHM_DSA, &formats, &len));
248 ExpectContains(KM_KEY_FORMAT_X509, formats, len);
249 free(formats);
Shawn Willden28e41472014-08-18 13:35:22 -0600250
Shawn Willden5b53c992015-02-02 08:05:25 -0700251 EXPECT_EQ(KM_ERROR_OK,
252 device()->get_supported_export_formats(device(), KM_ALGORITHM_ECDSA, &formats, &len));
253 ExpectContains(KM_KEY_FORMAT_X509, formats, len);
254 free(formats);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600255
Shawn Willden5b53c992015-02-02 08:05:25 -0700256 EXPECT_EQ(KM_ERROR_OK,
257 device()->get_supported_export_formats(device(), KM_ALGORITHM_AES, &formats, &len));
258 EXPECT_EQ(0, len);
259 free(formats);
Shawn Willden128ffe02014-08-06 12:31:33 -0600260}
261
Shawn Willdend0772312014-09-18 12:27:57 -0600262keymaster_key_param_t key_generation_base_params[] = {
Shawn Willden3809b932014-12-02 06:59:46 -0700263 Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN), Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY),
264 Authorization(TAG_USER_ID, 7), Authorization(TAG_USER_AUTH_ID, 8),
Shawn Willdend0772312014-09-18 12:27:57 -0600265 Authorization(TAG_APPLICATION_ID, "app_id", 6),
Shawn Willden3809b932014-12-02 06:59:46 -0700266 Authorization(TAG_APPLICATION_DATA, "app_data", 8), Authorization(TAG_AUTH_TIMEOUT, 300),
Shawn Willdend0772312014-09-18 12:27:57 -0600267};
268
Shawn Willden5b53c992015-02-02 08:05:25 -0700269TEST_F(KeymasterTest, TestFlags) {
270 EXPECT_TRUE(device()->flags & KEYMASTER_SOFTWARE_ONLY);
271 EXPECT_TRUE(device()->flags & KEYMASTER_BLOBS_ARE_STANDALONE);
272 EXPECT_FALSE(device()->flags & KEYMASTER_SUPPORTS_DSA);
273 EXPECT_TRUE(device()->flags & KEYMASTER_SUPPORTS_EC);
274}
275
276typedef KeymasterTest OldKeyGeneration;
277
278TEST_F(OldKeyGeneration, Rsa) {
279 keymaster_rsa_keygen_params_t params = {.modulus_size = 256, .public_exponent = 3};
280 uint8_t* key_blob;
281 size_t key_blob_length;
282 EXPECT_EQ(0,
283 device()->generate_keypair(device(), TYPE_RSA, &params, &key_blob, &key_blob_length));
284 EXPECT_GT(key_blob_length, 0);
285
286 free(key_blob);
287}
288
289TEST_F(OldKeyGeneration, Ecdsa) {
290
291 keymaster_ec_keygen_params_t params = {.field_size = 256};
292 uint8_t* key_blob;
293 size_t key_blob_length;
294 EXPECT_EQ(0,
295 device()->generate_keypair(device(), TYPE_EC, &params, &key_blob, &key_blob_length));
296 EXPECT_GT(key_blob_length, 0);
297
298 free(key_blob);
299}
300
Shawn Willdend0772312014-09-18 12:27:57 -0600301class NewKeyGeneration : public KeymasterTest {
302 protected:
303 NewKeyGeneration() {
Shawn Willden5b53c992015-02-02 08:05:25 -0700304 params_.Reinitialize(key_generation_base_params, array_length(key_generation_base_params));
Shawn Willdend0772312014-09-18 12:27:57 -0600305 }
306
Shawn Willden5b53c992015-02-02 08:05:25 -0700307 void CheckBaseParams(const AuthorizationSet& auths) {
308 EXPECT_TRUE(contains(auths, TAG_PURPOSE, KM_PURPOSE_SIGN));
309 EXPECT_TRUE(contains(auths, TAG_PURPOSE, KM_PURPOSE_VERIFY));
310 EXPECT_TRUE(contains(auths, TAG_USER_ID, 7));
311 EXPECT_TRUE(contains(auths, TAG_USER_AUTH_ID, 8));
312 EXPECT_TRUE(contains(auths, TAG_AUTH_TIMEOUT, 300));
Shawn Willdend0772312014-09-18 12:27:57 -0600313
314 // Verify that App ID, App data and ROT are NOT included.
Shawn Willden5b53c992015-02-02 08:05:25 -0700315 EXPECT_FALSE(contains(auths, TAG_ROOT_OF_TRUST));
316 EXPECT_FALSE(contains(auths, TAG_APPLICATION_ID));
317 EXPECT_FALSE(contains(auths, TAG_APPLICATION_DATA));
Shawn Willdend0772312014-09-18 12:27:57 -0600318
319 // Just for giggles, check that some unexpected tags/values are NOT present.
Shawn Willden5b53c992015-02-02 08:05:25 -0700320 EXPECT_FALSE(contains(auths, TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
321 EXPECT_FALSE(contains(auths, TAG_PURPOSE, KM_PURPOSE_DECRYPT));
322 EXPECT_FALSE(contains(auths, TAG_AUTH_TIMEOUT, 301));
Shawn Willdend0772312014-09-18 12:27:57 -0600323
324 // Now check that unspecified, defaulted tags are correct.
Shawn Willden5b53c992015-02-02 08:05:25 -0700325 EXPECT_TRUE(contains(auths, TAG_ORIGIN, KM_ORIGIN_SOFTWARE));
326 EXPECT_TRUE(contains(auths, KM_TAG_CREATION_DATETIME));
Shawn Willdend0772312014-09-18 12:27:57 -0600327 }
Shawn Willden2079ae82015-01-22 13:42:31 -0700328};
329
Shawn Willden5b53c992015-02-02 08:05:25 -0700330struct ParamListDelete {
331 void operator()(keymaster_key_param_set_t* p) { keymaster_free_param_set(p); }
332};
333
334typedef UniquePtr<keymaster_key_param_set_t, ParamListDelete> UniqueParamSetPtr;
335
Shawn Willden128ffe02014-08-06 12:31:33 -0600336TEST_F(NewKeyGeneration, Rsa) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700337 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA));
338 params_.push_back(Authorization(TAG_KEY_SIZE, 256));
339 params_.push_back(Authorization(TAG_RSA_PUBLIC_EXPONENT, 3));
340 ASSERT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
341 &characteristics_));
342 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
343 AuthorizationSet auths(characteristics_->sw_enforced);
344 CheckBaseParams(auths);
Shawn Willden128ffe02014-08-06 12:31:33 -0600345
Shawn Willden5b53c992015-02-02 08:05:25 -0700346 // Check specified tags are all present in auths
347 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_RSA));
348 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 256));
349 EXPECT_TRUE(contains(auths, TAG_RSA_PUBLIC_EXPONENT, 3));
Shawn Willden128ffe02014-08-06 12:31:33 -0600350}
351
Shawn Willden6bbe6782014-09-18 11:26:15 -0600352TEST_F(NewKeyGeneration, RsaDefaultSize) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700353 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA));
354 ASSERT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
355 &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600356
Shawn Willden5b53c992015-02-02 08:05:25 -0700357 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
358 AuthorizationSet auths(characteristics_->sw_enforced);
359 CheckBaseParams(auths);
Shawn Willden6bbe6782014-09-18 11:26:15 -0600360
Shawn Willden5b53c992015-02-02 08:05:25 -0700361 // Check specified tags are all present in auths
362 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_RSA));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600363
364 // Now check that unspecified, defaulted tags are correct.
Shawn Willden5b53c992015-02-02 08:05:25 -0700365 EXPECT_TRUE(contains(auths, TAG_RSA_PUBLIC_EXPONENT, 65537));
366 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 2048));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600367}
368
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600369TEST_F(NewKeyGeneration, Ecdsa) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700370 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
371 params_.push_back(Authorization(TAG_KEY_SIZE, 224));
372 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
373 &characteristics_));
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600374
Shawn Willden5b53c992015-02-02 08:05:25 -0700375 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
376 AuthorizationSet auths(characteristics_->sw_enforced);
377 CheckBaseParams(auths);
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600378
Shawn Willden5b53c992015-02-02 08:05:25 -0700379 // Check specified tags are all present in auths characteristics
380 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
381 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 224));
Shawn Willdenc3864dd2014-08-18 15:20:01 -0600382}
383
Shawn Willden6bbe6782014-09-18 11:26:15 -0600384TEST_F(NewKeyGeneration, EcdsaDefaultSize) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700385 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
386 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
387 &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600388
Shawn Willden5b53c992015-02-02 08:05:25 -0700389 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
390 AuthorizationSet auths(characteristics_->sw_enforced);
391 CheckBaseParams(auths);
Shawn Willden6bbe6782014-09-18 11:26:15 -0600392
Shawn Willden5b53c992015-02-02 08:05:25 -0700393 // Check specified tags are all present in auths
394 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600395
396 // Now check that unspecified, defaulted tags are correct.
Shawn Willden5b53c992015-02-02 08:05:25 -0700397 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 224));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600398}
399
400TEST_F(NewKeyGeneration, EcdsaInvalidSize) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700401 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
402 params_.push_back(Authorization(TAG_KEY_SIZE, 190));
403 EXPECT_EQ(KM_ERROR_UNSUPPORTED_KEY_SIZE,
404 device()->generate_key(device(), params_.data(), params_.size(), &blob_,
405 &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600406}
407
408TEST_F(NewKeyGeneration, EcdsaAllValidSizes) {
Shawn Willden8c856c82014-09-26 09:34:36 -0600409 size_t valid_sizes[] = {224, 256, 384, 521};
Shawn Willden6bbe6782014-09-18 11:26:15 -0600410 for (size_t size : valid_sizes) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700411 params_.Reinitialize(key_generation_base_params, array_length(key_generation_base_params));
412 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
413 params_.push_back(Authorization(TAG_KEY_SIZE, size));
414 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(),
415 &blob_, &characteristics_))
416 << "Failed to generate size: " << size;
417
418 FreeCharacteristics();
419 FreeKeyBlob();
Shawn Willden6bbe6782014-09-18 11:26:15 -0600420 }
421}
422
Shawn Willden19fca882015-01-22 16:35:30 -0700423TEST_F(NewKeyGeneration, AesOcb) {
424 keymaster_key_param_t params[] = {
425 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
426 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
427 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_KEY_SIZE, 128),
428 Authorization(TAG_BLOCK_MODE, KM_MODE_OCB), Authorization(TAG_CHUNK_LENGTH, 4096),
Shawn Willden7efb8782014-12-11 14:07:44 -0700429 Authorization(TAG_MAC_LENGTH, 16), Authorization(TAG_PADDING, KM_PAD_NONE),
Shawn Willden19fca882015-01-22 16:35:30 -0700430 };
Shawn Willden5b53c992015-02-02 08:05:25 -0700431 params_.Reinitialize(params, array_length(params));
432 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(), &blob_,
433 &characteristics_));
Shawn Willden19fca882015-01-22 16:35:30 -0700434}
435
436TEST_F(NewKeyGeneration, AesOcbInvalidKeySize) {
437 keymaster_key_param_t params[] = {
438 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
439 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
440 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_KEY_SIZE, 129),
441 Authorization(TAG_BLOCK_MODE, KM_MODE_OCB), Authorization(TAG_CHUNK_LENGTH, 4096),
Shawn Willden7efb8782014-12-11 14:07:44 -0700442 Authorization(TAG_MAC_LENGTH, 16), Authorization(TAG_PADDING, KM_PAD_NONE),
Shawn Willden19fca882015-01-22 16:35:30 -0700443 };
Shawn Willden5b53c992015-02-02 08:05:25 -0700444 params_.Reinitialize(params, array_length(params));
445 EXPECT_EQ(KM_ERROR_UNSUPPORTED_KEY_SIZE,
446 device()->generate_key(device(), params_.data(), params_.size(), &blob_,
447 &characteristics_));
Shawn Willden19fca882015-01-22 16:35:30 -0700448}
449
450TEST_F(NewKeyGeneration, AesOcbAllValidSizes) {
451 keymaster_key_param_t params[] = {
452 Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT),
453 Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT),
Shawn Willden7efb8782014-12-11 14:07:44 -0700454 Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES), Authorization(TAG_BLOCK_MODE, KM_MODE_OCB),
455 Authorization(TAG_MAC_LENGTH, 16), Authorization(TAG_CHUNK_LENGTH, 4096),
Shawn Willden19fca882015-01-22 16:35:30 -0700456 Authorization(TAG_PADDING, KM_PAD_NONE),
457 };
458
459 size_t valid_sizes[] = {128, 192, 256};
460 for (size_t size : valid_sizes) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700461 params_.Reinitialize(params, array_length(params));
462 params_.push_back(Authorization(TAG_KEY_SIZE, size));
463 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(),
464 &blob_, &characteristics_))
465 << "Failed to generate size: " << size;
466
467 FreeCharacteristics();
468 FreeKeyBlob();
Shawn Willden19fca882015-01-22 16:35:30 -0700469 }
470}
471
Shawn Willden76364712014-08-11 17:48:04 -0600472typedef KeymasterTest GetKeyCharacteristics;
473TEST_F(GetKeyCharacteristics, SimpleRsa) {
474 keymaster_key_param_t params[] = {
Shawn Willden3809b932014-12-02 06:59:46 -0700475 Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN), Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY),
476 Authorization(TAG_ALGORITHM, KM_ALGORITHM_RSA), Authorization(TAG_KEY_SIZE, 256),
477 Authorization(TAG_USER_ID, 7), Authorization(TAG_USER_AUTH_ID, 8),
478 Authorization(TAG_APPLICATION_ID, "app_id", 6), Authorization(TAG_AUTH_TIMEOUT, 300),
Shawn Willden76364712014-08-11 17:48:04 -0600479 };
480
Shawn Willden5b53c992015-02-02 08:05:25 -0700481 ASSERT_EQ(KM_ERROR_OK, device()->generate_key(device(), params, array_length(params), &blob_,
482 &characteristics_));
483 AuthorizationSet original(characteristics_->sw_enforced);
484 FreeCharacteristics();
Shawn Willden76364712014-08-11 17:48:04 -0600485
Shawn Willden5b53c992015-02-02 08:05:25 -0700486 keymaster_blob_t client_id = {.data = reinterpret_cast<const uint8_t*>("app_id"),
487 .data_length = 6};
488 ASSERT_EQ(KM_ERROR_OK,
489 device()->get_key_characteristics(device(), &blob_, &client_id, NULL /* app_data */,
490 &characteristics_));
491 EXPECT_EQ(original, AuthorizationSet(characteristics_->sw_enforced));
Shawn Willden76364712014-08-11 17:48:04 -0600492}
493
Shawn Willden61644f32014-08-18 13:43:14 -0600494/**
495 * Test class that provides some infrastructure for generating keys and signing messages.
496 */
Shawn Willden1615f2e2014-08-13 10:37:40 -0600497class SigningOperationsTest : public KeymasterTest {
498 protected:
Shawn Willden5b53c992015-02-02 08:05:25 -0700499 SigningOperationsTest() : out_params_(NULL), output_(NULL), signature_(NULL) {}
500 ~SigningOperationsTest() {
501 // Clean up so (most) tests won't have to.
502 FreeOutput();
503 FreeSignature();
504 }
505
Shawn Willden61644f32014-08-18 13:43:14 -0600506 void GenerateKey(keymaster_algorithm_t algorithm, keymaster_digest_t digest,
507 keymaster_padding_t padding, uint32_t key_size) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700508 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN));
509 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY));
510 params_.push_back(Authorization(TAG_ALGORITHM, algorithm));
511 params_.push_back(Authorization(TAG_KEY_SIZE, key_size));
512 params_.push_back(Authorization(TAG_USER_ID, 7));
513 params_.push_back(Authorization(TAG_USER_AUTH_ID, 8));
514 params_.push_back(Authorization(TAG_APPLICATION_ID, "app_id", 6));
515 params_.push_back(Authorization(TAG_AUTH_TIMEOUT, 300));
Shawn Willden43e999e2014-08-13 13:29:50 -0600516 if (static_cast<int>(digest) != -1)
Shawn Willden5b53c992015-02-02 08:05:25 -0700517 params_.push_back(TAG_DIGEST, digest);
Shawn Willden43e999e2014-08-13 13:29:50 -0600518 if (static_cast<int>(padding) != -1)
Shawn Willden5b53c992015-02-02 08:05:25 -0700519 params_.push_back(TAG_PADDING, padding);
520
521 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params_.data(), params_.size(),
522 &blob_, &characteristics_));
Shawn Willden61644f32014-08-18 13:43:14 -0600523 }
Shawn Willden1615f2e2014-08-13 10:37:40 -0600524
Shawn Willden61644f32014-08-18 13:43:14 -0600525 void SignMessage(const void* message, size_t size) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700526 EXPECT_EQ(KM_ERROR_OK, device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
527 array_length(client_params_), &out_params_,
528 &out_params_count_, &op_handle_));
529
530 EXPECT_EQ(KM_ERROR_OK,
531 device()->update(device(), op_handle_, reinterpret_cast<const uint8_t*>(message),
532 size, &input_consumed_, &output_, &output_length_));
533 EXPECT_EQ(0, output_length_);
534 FreeOutput();
535 EXPECT_EQ(size, input_consumed_);
536
537 EXPECT_EQ(KM_ERROR_OK,
538 device()->finish(device(), op_handle_, NULL /* signature to verify */,
539 0 /* signature to verify length */, &signature_,
540 &signature_length_));
541 EXPECT_GT(signature_length_, 0);
Shawn Willden437fbd12014-08-20 11:59:49 -0600542 }
543
Shawn Willden5b53c992015-02-02 08:05:25 -0700544 void FreeOutput() {
545 free(out_params_);
546 out_params_ = NULL;
547 free(output_);
548 output_ = NULL;
Shawn Willden61644f32014-08-18 13:43:14 -0600549 }
550
Shawn Willden5b53c992015-02-02 08:05:25 -0700551 void FreeSignature() {
552 free(signature_);
553 signature_ = NULL;
Shawn Willdenf268d742014-08-19 15:36:26 -0600554 }
555
Shawn Willden5b53c992015-02-02 08:05:25 -0700556 void corrupt_key_blob() {
557 uint8_t* tmp = const_cast<uint8_t*>(blob_.key_material);
558 ++tmp[blob_.key_material_size / 2];
Shawn Willden1615f2e2014-08-13 10:37:40 -0600559 }
560
Shawn Willden5b53c992015-02-02 08:05:25 -0700561 keymaster_blob_t client_id_ = {.data = reinterpret_cast<const uint8_t*>("app_id"),
562 .data_length = 6};
563 keymaster_key_param_t client_params_[1] = {
564 Authorization(TAG_APPLICATION_ID, client_id_.data, client_id_.data_length)};
565 keymaster_key_param_t* out_params_;
566 size_t out_params_count_;
567 uint64_t op_handle_;
568 size_t input_consumed_;
569 uint8_t* output_;
570 size_t output_length_;
571 uint8_t* signature_;
572 size_t signature_length_;
Shawn Willden1615f2e2014-08-13 10:37:40 -0600573};
574
575TEST_F(SigningOperationsTest, RsaSuccess) {
Shawn Willden61644f32014-08-18 13:43:14 -0600576 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
Shawn Willdenffd790c2014-08-18 21:20:06 -0600577 const char message[] = "12345678901234567890123456789012";
Shawn Willdend05cba52014-09-26 09:58:12 -0600578 SignMessage(message, array_size(message) - 1);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600579}
580
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600581TEST_F(SigningOperationsTest, EcdsaSuccess) {
Shawn Willden8c856c82014-09-26 09:34:36 -0600582 GenerateKey(KM_ALGORITHM_ECDSA, KM_DIGEST_NONE, KM_PAD_NONE, 224 /* key size */);
Shawn Willdend05cba52014-09-26 09:58:12 -0600583 const char message[] = "123456789012345678901234567890123456789012345678";
584 SignMessage(message, array_size(message) - 1);
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600585}
586
Shawn Willden1615f2e2014-08-13 10:37:40 -0600587TEST_F(SigningOperationsTest, RsaAbort) {
Shawn Willden61644f32014-08-18 13:43:14 -0600588 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
Shawn Willden5b53c992015-02-02 08:05:25 -0700589 ASSERT_EQ(KM_ERROR_OK, device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
590 array_length(client_params_), &out_params_,
591 &out_params_count_, &op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600592
Shawn Willden5b53c992015-02-02 08:05:25 -0700593 EXPECT_EQ(KM_ERROR_OK, device()->abort(device(), op_handle_));
594 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600595}
596
597TEST_F(SigningOperationsTest, RsaUnsupportedDigest) {
Shawn Willden61644f32014-08-18 13:43:14 -0600598 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_SHA_2_256, KM_PAD_NONE, 256 /* key size */);
Shawn Willden5b53c992015-02-02 08:05:25 -0700599 ASSERT_EQ(KM_ERROR_UNSUPPORTED_DIGEST,
600 device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
601 array_length(client_params_), &out_params_, &out_params_count_,
602 &op_handle_));
603 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600604}
605
606TEST_F(SigningOperationsTest, RsaUnsupportedPadding) {
Shawn Willden61644f32014-08-18 13:43:14 -0600607 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_RSA_OAEP, 256 /* key size */);
Shawn Willden5b53c992015-02-02 08:05:25 -0700608 ASSERT_EQ(KM_ERROR_UNSUPPORTED_PADDING_MODE,
609 device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
610 array_length(client_params_), &out_params_, &out_params_count_,
611 &op_handle_));
612 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600613}
614
615TEST_F(SigningOperationsTest, RsaNoDigest) {
Shawn Willden61644f32014-08-18 13:43:14 -0600616 GenerateKey(KM_ALGORITHM_RSA, static_cast<keymaster_digest_t>(-1), KM_PAD_NONE,
617 256 /* key size */);
Shawn Willden5b53c992015-02-02 08:05:25 -0700618 ASSERT_EQ(KM_ERROR_UNSUPPORTED_DIGEST,
619 device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
620 array_length(client_params_), &out_params_, &out_params_count_,
621 &op_handle_));
622 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600623}
624
625TEST_F(SigningOperationsTest, RsaNoPadding) {
Shawn Willden61644f32014-08-18 13:43:14 -0600626 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, static_cast<keymaster_padding_t>(-1),
627 256 /* key size */);
Shawn Willden5b53c992015-02-02 08:05:25 -0700628 ASSERT_EQ(KM_ERROR_UNSUPPORTED_PADDING_MODE,
629 device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
630 array_length(client_params_), &out_params_, &out_params_count_,
631 &op_handle_));
632 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600633}
634
635TEST_F(SigningOperationsTest, RsaTooShortMessage) {
Shawn Willden61644f32014-08-18 13:43:14 -0600636 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
Shawn Willden5b53c992015-02-02 08:05:25 -0700637 ASSERT_EQ(KM_ERROR_OK, device()->begin(device(), KM_PURPOSE_SIGN, &blob_, client_params_,
638 array_length(client_params_), &out_params_,
639 &out_params_count_, &op_handle_));
640 ASSERT_EQ(KM_ERROR_OK,
641 device()->update(device(), op_handle_,
642 reinterpret_cast<const uint8_t*>("01234567890123456789012345678901"),
643 31, &input_consumed_, &output_, &output_length_));
644 EXPECT_EQ(0U, output_length_);
645 EXPECT_EQ(31U, input_consumed_);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600646
Shawn Willden5b53c992015-02-02 08:05:25 -0700647 ASSERT_EQ(KM_ERROR_UNKNOWN_ERROR,
648 device()->finish(device(), op_handle_, NULL, 0, &signature_, &signature_length_));
Shawn Willden1615f2e2014-08-13 10:37:40 -0600649
Shawn Willden5b53c992015-02-02 08:05:25 -0700650 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willden43e999e2014-08-13 13:29:50 -0600651}
652
Shawn Willdend05cba52014-09-26 09:58:12 -0600653class VerificationOperationsTest : public SigningOperationsTest {
654 protected:
655 void VerifyMessage(const void* message, size_t message_len) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700656 EXPECT_TRUE(signature_ != NULL);
Shawn Willdend05cba52014-09-26 09:58:12 -0600657
Shawn Willden5b53c992015-02-02 08:05:25 -0700658 EXPECT_EQ(KM_ERROR_OK, device()->begin(device(), KM_PURPOSE_VERIFY, &blob_, client_params_,
659 array_length(client_params_), &out_params_,
660 &out_params_count_, &op_handle_));
661 ASSERT_EQ(KM_ERROR_OK,
662 device()->update(device(), op_handle_, reinterpret_cast<const uint8_t*>(message),
663 message_len, &input_consumed_, &output_, &output_length_));
664 EXPECT_EQ(0U, output_length_);
665 FreeOutput();
666 EXPECT_EQ(message_len, input_consumed_);
Shawn Willdend05cba52014-09-26 09:58:12 -0600667
Shawn Willden5b53c992015-02-02 08:05:25 -0700668 ASSERT_EQ(KM_ERROR_OK, device()->finish(device(), op_handle_, signature_, signature_length_,
669 &output_, &output_length_));
670 EXPECT_EQ(0U, output_length_);
Shawn Willdend05cba52014-09-26 09:58:12 -0600671
Shawn Willden5b53c992015-02-02 08:05:25 -0700672 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle_));
Shawn Willdend05cba52014-09-26 09:58:12 -0600673 }
674};
675
Shawn Willden43e999e2014-08-13 13:29:50 -0600676TEST_F(VerificationOperationsTest, RsaSuccess) {
Shawn Willden61644f32014-08-18 13:43:14 -0600677 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
678 const char message[] = "12345678901234567890123456789012";
679 SignMessage(message, array_size(message) - 1);
Shawn Willdend05cba52014-09-26 09:58:12 -0600680 VerifyMessage(message, array_size(message) - 1);
Shawn Willden1615f2e2014-08-13 10:37:40 -0600681}
682
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600683TEST_F(VerificationOperationsTest, EcdsaSuccess) {
Shawn Willden8c856c82014-09-26 09:34:36 -0600684 GenerateKey(KM_ALGORITHM_ECDSA, KM_DIGEST_NONE, KM_PAD_NONE, 224 /* key size */);
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600685 const char message[] = "123456789012345678901234567890123456789012345678";
686 SignMessage(message, array_size(message) - 1);
Shawn Willdend05cba52014-09-26 09:58:12 -0600687 VerifyMessage(message, array_size(message) - 1);
Shawn Willden5ac2f8f2014-08-18 15:33:10 -0600688}
689
Shawn Willden5b53c992015-02-02 08:05:25 -0700690typedef VerificationOperationsTest ExportKeyTest;
Shawn Willdenffd790c2014-08-18 21:20:06 -0600691TEST_F(ExportKeyTest, RsaSuccess) {
692 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256 /* key size */);
Shawn Willdenffd790c2014-08-18 21:20:06 -0600693
Shawn Willden5b53c992015-02-02 08:05:25 -0700694 uint8_t* export_data;
695 size_t export_data_length;
696 ASSERT_EQ(KM_ERROR_OK,
697 device()->export_key(device(), KM_KEY_FORMAT_X509, &blob_, &client_id_,
698 NULL /* app_data */, &export_data, &export_data_length));
699 EXPECT_TRUE(export_data != NULL);
700 EXPECT_GT(export_data_length, 0);
Shawn Willdene46a43f2014-08-27 10:35:36 -0600701
702 // TODO(swillden): Verify that the exported key is actually usable to verify signatures.
Shawn Willden5b53c992015-02-02 08:05:25 -0700703 free(export_data);
Shawn Willdenffd790c2014-08-18 21:20:06 -0600704}
705
Shawn Willdenf268d742014-08-19 15:36:26 -0600706TEST_F(ExportKeyTest, EcdsaSuccess) {
Shawn Willden8c856c82014-09-26 09:34:36 -0600707 GenerateKey(KM_ALGORITHM_ECDSA, KM_DIGEST_NONE, KM_PAD_NONE, 224 /* key size */);
Shawn Willdenf268d742014-08-19 15:36:26 -0600708
Shawn Willden5b53c992015-02-02 08:05:25 -0700709 uint8_t* export_data;
710 size_t export_data_length;
711 ASSERT_EQ(KM_ERROR_OK,
712 device()->export_key(device(), KM_KEY_FORMAT_X509, &blob_, &client_id_,
713 NULL /* app_data */, &export_data, &export_data_length));
714 EXPECT_TRUE(export_data != NULL);
715 EXPECT_GT(export_data_length, 0);
Shawn Willdene46a43f2014-08-27 10:35:36 -0600716
717 // TODO(swillden): Verify that the exported key is actually usable to verify signatures.
Shawn Willden5b53c992015-02-02 08:05:25 -0700718 free(export_data);
Shawn Willdenf268d742014-08-19 15:36:26 -0600719}
720
721TEST_F(ExportKeyTest, RsaUnsupportedKeyFormat) {
722 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256);
723
Shawn Willden5b53c992015-02-02 08:05:25 -0700724 uint8_t dummy[] = {1};
725 uint8_t* export_data = dummy; // So it's not NULL;
726 size_t export_data_length;
727 ASSERT_EQ(KM_ERROR_UNSUPPORTED_KEY_FORMAT,
728 device()->export_key(device(), KM_KEY_FORMAT_PKCS8, &blob_, &client_id_,
729 NULL /* app_data */, &export_data, &export_data_length));
730 ASSERT_TRUE(export_data == NULL);
Shawn Willdenf268d742014-08-19 15:36:26 -0600731}
732
733TEST_F(ExportKeyTest, RsaCorruptedKeyBlob) {
734 GenerateKey(KM_ALGORITHM_RSA, KM_DIGEST_NONE, KM_PAD_NONE, 256);
Shawn Willden5b53c992015-02-02 08:05:25 -0700735 corrupt_key_blob();
Shawn Willdenf268d742014-08-19 15:36:26 -0600736
Shawn Willden5b53c992015-02-02 08:05:25 -0700737 uint8_t dummy[] = {1};
738 uint8_t* export_data = dummy; // So it's not NULL
739 size_t export_data_length;
740 ASSERT_EQ(KM_ERROR_INVALID_KEY_BLOB,
741 device()->export_key(device(), KM_KEY_FORMAT_X509, &blob_, &client_id_,
742 NULL /* app_data */, &export_data, &export_data_length));
743 ASSERT_TRUE(export_data == NULL);
Shawn Willdenf268d742014-08-19 15:36:26 -0600744}
745
Shawn Willden437fbd12014-08-20 11:59:49 -0600746static string read_file(const string& file_name) {
747 ifstream file_stream(file_name, std::ios::binary);
748 istreambuf_iterator<char> file_begin(file_stream);
749 istreambuf_iterator<char> file_end;
750 return string(file_begin, file_end);
751}
752
Shawn Willden5b53c992015-02-02 08:05:25 -0700753class ImportKeyTest : public VerificationOperationsTest {
754 protected:
755 ImportKeyTest() {
756 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_SIGN));
757 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_VERIFY));
758 params_.push_back(Authorization(TAG_DIGEST, KM_DIGEST_NONE));
759 params_.push_back(Authorization(TAG_PADDING, KM_PAD_NONE));
760 params_.push_back(Authorization(TAG_USER_ID, 7));
761 params_.push_back(Authorization(TAG_USER_AUTH_ID, 8));
762 params_.push_back(Authorization(TAG_APPLICATION_ID, "app_id", 6));
763 params_.push_back(Authorization(TAG_AUTH_TIMEOUT, 300));
764 }
765};
Brian Carlstromecf2ae92015-01-29 09:56:10 -0800766
Shawn Willden5b53c992015-02-02 08:05:25 -0700767TEST_F(ImportKeyTest, RsaSuccess) {
Shawn Willden81effc62014-08-27 10:08:46 -0600768 string pk8_key = read_file("rsa_privkey_pk8.der");
Shawn Willden437fbd12014-08-20 11:59:49 -0600769 ASSERT_EQ(633U, pk8_key.size());
770
Shawn Willden5b53c992015-02-02 08:05:25 -0700771 ASSERT_EQ(KM_ERROR_OK,
772 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
773 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
774 &blob_, &characteristics_));
775 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
776 AuthorizationSet auths(characteristics_->sw_enforced);
Shawn Willden437fbd12014-08-20 11:59:49 -0600777
778 // Check values derived from the key.
Shawn Willden5b53c992015-02-02 08:05:25 -0700779 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_RSA));
780 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 1024));
781 EXPECT_TRUE(contains(auths, TAG_RSA_PUBLIC_EXPONENT, 65537U));
Shawn Willden437fbd12014-08-20 11:59:49 -0600782
783 // And values provided by GoogleKeymaster
Shawn Willden5b53c992015-02-02 08:05:25 -0700784 EXPECT_TRUE(contains(auths, TAG_ORIGIN, KM_ORIGIN_IMPORTED));
785 EXPECT_TRUE(contains(auths, KM_TAG_CREATION_DATETIME));
Shawn Willden437fbd12014-08-20 11:59:49 -0600786
787 size_t message_len = 1024 / 8;
788 UniquePtr<uint8_t[]> message(new uint8_t[message_len]);
789 std::fill(message.get(), message.get() + message_len, 'a');
Shawn Willden5b53c992015-02-02 08:05:25 -0700790 SignMessage(message.get(), message_len);
791 VerifyMessage(message.get(), message_len);
Shawn Willden437fbd12014-08-20 11:59:49 -0600792}
793
Shawn Willden6bbe6782014-09-18 11:26:15 -0600794TEST_F(ImportKeyTest, RsaKeySizeMismatch) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700795 params_.push_back(Authorization(TAG_KEY_SIZE, 2048)); // Doesn't match key
Shawn Willden6bbe6782014-09-18 11:26:15 -0600796
797 string pk8_key = read_file("rsa_privkey_pk8.der");
798 ASSERT_EQ(633U, pk8_key.size());
799
Shawn Willden5b53c992015-02-02 08:05:25 -0700800 ASSERT_EQ(KM_ERROR_IMPORT_PARAMETER_MISMATCH,
801 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
802 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
803 &blob_, &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600804}
805
806TEST_F(ImportKeyTest, RsaPublicExponenMismatch) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700807 params_.push_back(Authorization(TAG_RSA_PUBLIC_EXPONENT, 3)); // Doesn't match key
Shawn Willden6bbe6782014-09-18 11:26:15 -0600808
809 string pk8_key = read_file("rsa_privkey_pk8.der");
810 ASSERT_EQ(633U, pk8_key.size());
811
Shawn Willden5b53c992015-02-02 08:05:25 -0700812 ASSERT_EQ(KM_ERROR_IMPORT_PARAMETER_MISMATCH,
813 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
814 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
815 &blob_, &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600816}
817
Shawn Willden81effc62014-08-27 10:08:46 -0600818TEST_F(ImportKeyTest, EcdsaSuccess) {
Shawn Willden81effc62014-08-27 10:08:46 -0600819 string pk8_key = read_file("ec_privkey_pk8.der");
820 ASSERT_EQ(138U, pk8_key.size());
821
Shawn Willden5b53c992015-02-02 08:05:25 -0700822 ASSERT_EQ(KM_ERROR_OK,
823 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
824 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
825 &blob_, &characteristics_));
826 EXPECT_EQ(0U, characteristics_->hw_enforced.length);
827 AuthorizationSet auths(characteristics_->sw_enforced);
Shawn Willden81effc62014-08-27 10:08:46 -0600828
829 // Check values derived from the key.
Shawn Willden5b53c992015-02-02 08:05:25 -0700830 EXPECT_TRUE(contains(auths, TAG_ALGORITHM, KM_ALGORITHM_ECDSA));
831 EXPECT_TRUE(contains(auths, TAG_KEY_SIZE, 256));
Shawn Willden81effc62014-08-27 10:08:46 -0600832
833 // And values provided by GoogleKeymaster
Shawn Willden5b53c992015-02-02 08:05:25 -0700834 EXPECT_TRUE(contains(auths, TAG_ORIGIN, KM_ORIGIN_IMPORTED));
835 EXPECT_TRUE(contains(auths, KM_TAG_CREATION_DATETIME));
Shawn Willden81effc62014-08-27 10:08:46 -0600836
Shawn Willden5b53c992015-02-02 08:05:25 -0700837 size_t message_len = 1024;
Shawn Willden81effc62014-08-27 10:08:46 -0600838 UniquePtr<uint8_t[]> message(new uint8_t[message_len]);
839 std::fill(message.get(), message.get() + message_len, 'a');
Shawn Willden5b53c992015-02-02 08:05:25 -0700840 SignMessage(message.get(), message_len);
841 VerifyMessage(message.get(), message_len);
Shawn Willden81effc62014-08-27 10:08:46 -0600842}
843
Shawn Willden5b53c992015-02-02 08:05:25 -0700844TEST_F(ImportKeyTest, EcdsaKeySizeMismatch) {
845 params_.push_back(Authorization(TAG_KEY_SIZE, 224)); // Doesn't match key
Shawn Willden6bbe6782014-09-18 11:26:15 -0600846
Shawn Willden5b53c992015-02-02 08:05:25 -0700847 string pk8_key = read_file("rsa_privkey_pk8.der");
848 ASSERT_EQ(633U, pk8_key.size());
Shawn Willden6bbe6782014-09-18 11:26:15 -0600849
Shawn Willden5b53c992015-02-02 08:05:25 -0700850 ASSERT_EQ(KM_ERROR_IMPORT_PARAMETER_MISMATCH,
851 device()->import_key(device(), params_.data(), params_.size(), KM_KEY_FORMAT_PKCS8,
852 reinterpret_cast<const uint8_t*>(pk8_key.data()), pk8_key.size(),
853 &blob_, &characteristics_));
Shawn Willden6bbe6782014-09-18 11:26:15 -0600854}
855
Shawn Willden2665e862014-11-24 14:46:21 -0700856typedef KeymasterTest VersionTest;
857TEST_F(VersionTest, GetVersion) {
858 GetVersionRequest req;
859 GetVersionResponse rsp;
Shawn Willden5b53c992015-02-02 08:05:25 -0700860 device_.GetVersion(req, &rsp);
Shawn Willden2665e862014-11-24 14:46:21 -0700861 EXPECT_EQ(KM_ERROR_OK, rsp.error);
862 EXPECT_EQ(1, rsp.major_ver);
863 EXPECT_EQ(0, rsp.minor_ver);
864 EXPECT_EQ(0, rsp.subminor_ver);
865}
866
Shawn Willden4200f212014-12-02 07:01:21 -0700867/**
868 * Test class that provides some infrastructure for generating keys and encrypting messages.
869 */
870class EncryptionOperationsTest : public KeymasterTest {
871 protected:
Shawn Willdenbe4a2a32014-12-15 14:51:10 -0700872 void GenerateKey(AuthorizationSet* params) {
873 FreeKeyBlob();
874 FreeCharacteristics();
875 AddClientParams(params);
876 EXPECT_EQ(KM_ERROR_OK, device()->generate_key(device(), params->data(), params->size(),
877 &blob_, &characteristics_));
878 }
879
Shawn Willden4200f212014-12-02 07:01:21 -0700880 void GenerateKey(keymaster_algorithm_t algorithm, keymaster_padding_t padding,
881 uint32_t key_size) {
Shawn Willden6dde87c2014-12-11 14:08:48 -0700882 params_.Clear();
Shawn Willden5b53c992015-02-02 08:05:25 -0700883 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
884 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT));
885 params_.push_back(Authorization(TAG_ALGORITHM, algorithm));
886 params_.push_back(Authorization(TAG_KEY_SIZE, key_size));
887 params_.push_back(Authorization(TAG_USER_ID, 7));
888 params_.push_back(Authorization(TAG_USER_AUTH_ID, 8));
Shawn Willden5b53c992015-02-02 08:05:25 -0700889 params_.push_back(Authorization(TAG_AUTH_TIMEOUT, 300));
Shawn Willden4200f212014-12-02 07:01:21 -0700890 if (static_cast<int>(padding) != -1)
Shawn Willden5b53c992015-02-02 08:05:25 -0700891 params_.push_back(TAG_PADDING, padding);
Shawn Willden6dde87c2014-12-11 14:08:48 -0700892
Shawn Willdenbe4a2a32014-12-15 14:51:10 -0700893 GenerateKey(&params_);
Shawn Willden4200f212014-12-02 07:01:21 -0700894 }
895
Shawn Willden907c3012014-12-08 15:51:55 -0700896 void GenerateSymmetricKey(keymaster_algorithm_t algorithm, uint32_t key_size,
897 keymaster_block_mode_t block_mode, uint32_t chunk_length) {
Shawn Willden6dde87c2014-12-11 14:08:48 -0700898 params_.Clear();
Shawn Willden5b53c992015-02-02 08:05:25 -0700899 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
900 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT));
901 params_.push_back(Authorization(TAG_ALGORITHM, algorithm));
902 params_.push_back(Authorization(TAG_BLOCK_MODE, block_mode));
903 params_.push_back(Authorization(TAG_CHUNK_LENGTH, chunk_length));
904 params_.push_back(Authorization(TAG_KEY_SIZE, key_size));
905 params_.push_back(Authorization(TAG_MAC_LENGTH, 16));
906 params_.push_back(Authorization(TAG_USER_ID, 7));
907 params_.push_back(Authorization(TAG_USER_AUTH_ID, 8));
Shawn Willden5b53c992015-02-02 08:05:25 -0700908 params_.push_back(Authorization(TAG_AUTH_TIMEOUT, 300));
909
Shawn Willdenbe4a2a32014-12-15 14:51:10 -0700910 GenerateKey(&params_);
Shawn Willden907c3012014-12-08 15:51:55 -0700911 }
912
Shawn Willden4200f212014-12-02 07:01:21 -0700913 keymaster_error_t BeginOperation(keymaster_purpose_t purpose,
914 const keymaster_key_blob_t& key_blob, uint64_t* op_handle) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700915 return device()->begin(device(), purpose, &key_blob, client_params_,
916 array_length(client_params_), &out_params_, &out_params_count_,
917 op_handle);
Shawn Willden4200f212014-12-02 07:01:21 -0700918 }
919
920 keymaster_error_t UpdateOperation(uint64_t op_handle, const void* message, size_t size,
Shawn Willdenb7361132014-12-08 08:15:14 -0700921 string* output, size_t* input_consumed) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700922 uint8_t* out_tmp = NULL;
923 size_t out_length;
924 keymaster_error_t error =
925 device()->update(device(), op_handle, reinterpret_cast<const uint8_t*>(message), size,
926 input_consumed, &out_tmp, &out_length);
927 if (out_tmp)
Shawn Willden6dde87c2014-12-11 14:08:48 -0700928 output->append(reinterpret_cast<char*>(out_tmp), out_length);
Shawn Willden5b53c992015-02-02 08:05:25 -0700929 free(out_tmp);
930 return error;
Shawn Willden4200f212014-12-02 07:01:21 -0700931 }
932
933 keymaster_error_t FinishOperation(uint64_t op_handle, string* output) {
Shawn Willden5b53c992015-02-02 08:05:25 -0700934 uint8_t* out_tmp = NULL;
935 size_t out_length;
936 keymaster_error_t error = device()->finish(device(), op_handle, NULL /* signature */,
937 0 /* signature_length */, &out_tmp, &out_length);
938 if (out_tmp)
Shawn Willden6dde87c2014-12-11 14:08:48 -0700939 output->append(reinterpret_cast<char*>(out_tmp), out_length);
Shawn Willden5b53c992015-02-02 08:05:25 -0700940 free(out_tmp);
941 return error;
Shawn Willden4200f212014-12-02 07:01:21 -0700942 }
943
944 string ProcessMessage(keymaster_purpose_t purpose, const keymaster_key_blob_t& key_blob,
945 const void* message, size_t size) {
946 uint64_t op_handle;
947 EXPECT_EQ(KM_ERROR_OK, BeginOperation(purpose, key_blob, &op_handle));
948
949 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -0700950 size_t input_consumed;
951 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, message, size, &result, &input_consumed));
952 EXPECT_EQ(size, input_consumed);
Shawn Willden4200f212014-12-02 07:01:21 -0700953 EXPECT_EQ(KM_ERROR_OK, FinishOperation(op_handle, &result));
Shawn Willden6dde87c2014-12-11 14:08:48 -0700954 EXPECT_EQ(KM_ERROR_INVALID_OPERATION_HANDLE, device()->abort(device(), op_handle));
Shawn Willden4200f212014-12-02 07:01:21 -0700955 return result;
956 }
957
Shawn Willden6dde87c2014-12-11 14:08:48 -0700958 string EncryptMessage(const string& message) {
959 return ProcessMessage(KM_PURPOSE_ENCRYPT, blob_, message.c_str(), message.length());
Shawn Willden4200f212014-12-02 07:01:21 -0700960 }
961
Shawn Willden6dde87c2014-12-11 14:08:48 -0700962 string DecryptMessage(const string& ciphertext) {
963 return ProcessMessage(KM_PURPOSE_DECRYPT, blob_, ciphertext.c_str(), ciphertext.length());
Shawn Willden4200f212014-12-02 07:01:21 -0700964 }
965
966 void AddClientParams(AuthorizationSet* set) { set->push_back(TAG_APPLICATION_ID, "app_id", 6); }
967
Shawn Willden5b53c992015-02-02 08:05:25 -0700968 const void corrupt_key_blob() {
969 uint8_t* tmp = const_cast<uint8_t*>(blob_.key_material);
970 ++tmp[blob_.key_material_size / 2];
Shawn Willden4200f212014-12-02 07:01:21 -0700971 }
972
Shawn Willden5b53c992015-02-02 08:05:25 -0700973 keymaster_blob_t client_id_ = {.data = reinterpret_cast<const uint8_t*>("app_id"),
974 .data_length = 6};
975 keymaster_key_param_t client_params_[1] = {
976 Authorization(TAG_APPLICATION_ID, client_id_.data, client_id_.data_length)};
977
978 keymaster_key_param_t* out_params_;
979 size_t out_params_count_;
Shawn Willden4200f212014-12-02 07:01:21 -0700980};
981
982TEST_F(EncryptionOperationsTest, RsaOaepSuccess) {
983 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_OAEP, 512);
984 const char message[] = "Hello World!";
Shawn Willden6dde87c2014-12-11 14:08:48 -0700985 string ciphertext1 = EncryptMessage(string(message));
Shawn Willden4200f212014-12-02 07:01:21 -0700986 EXPECT_EQ(512 / 8, ciphertext1.size());
987
Shawn Willden6dde87c2014-12-11 14:08:48 -0700988 string ciphertext2 = EncryptMessage(string(message));
Shawn Willden4200f212014-12-02 07:01:21 -0700989 EXPECT_EQ(512 / 8, ciphertext2.size());
990
991 // OAEP randomizes padding so every result should be different.
992 EXPECT_NE(ciphertext1, ciphertext2);
993}
994
995TEST_F(EncryptionOperationsTest, RsaOaepRoundTrip) {
996 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_OAEP, 512);
997 const char message[] = "Hello World!";
Shawn Willden6dde87c2014-12-11 14:08:48 -0700998 string ciphertext = EncryptMessage(string(message));
Shawn Willden4200f212014-12-02 07:01:21 -0700999 EXPECT_EQ(512 / 8, ciphertext.size());
1000
Shawn Willden6dde87c2014-12-11 14:08:48 -07001001 string plaintext = DecryptMessage(ciphertext);
Shawn Willden4200f212014-12-02 07:01:21 -07001002 EXPECT_EQ(message, plaintext);
1003}
1004
1005TEST_F(EncryptionOperationsTest, RsaOaepTooLarge) {
1006 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_OAEP, 512);
1007 const char message[] = "12345678901234567890123";
1008 uint64_t op_handle;
1009 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -07001010 size_t input_consumed;
Shawn Willden4200f212014-12-02 07:01:21 -07001011
Shawn Willden5b53c992015-02-02 08:05:25 -07001012 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_ENCRYPT, blob_, &op_handle));
Shawn Willdenb7361132014-12-08 08:15:14 -07001013 EXPECT_EQ(KM_ERROR_OK,
1014 UpdateOperation(op_handle, message, array_size(message), &result, &input_consumed));
Shawn Willden4200f212014-12-02 07:01:21 -07001015 EXPECT_EQ(KM_ERROR_INVALID_INPUT_LENGTH, FinishOperation(op_handle, &result));
1016 EXPECT_EQ(0, result.size());
1017}
1018
1019TEST_F(EncryptionOperationsTest, RsaOaepCorruptedDecrypt) {
1020 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_OAEP, 512);
1021 const char message[] = "Hello World!";
Shawn Willden6dde87c2014-12-11 14:08:48 -07001022 string ciphertext = EncryptMessage(string(message));
Shawn Willden4200f212014-12-02 07:01:21 -07001023 EXPECT_EQ(512 / 8, ciphertext.size());
1024
1025 // Corrupt the ciphertext
1026 ciphertext[512 / 8 / 2]++;
1027
1028 uint64_t op_handle;
1029 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -07001030 size_t input_consumed;
Shawn Willden5b53c992015-02-02 08:05:25 -07001031 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_DECRYPT, blob_, &op_handle));
Shawn Willdenb7361132014-12-08 08:15:14 -07001032 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, ciphertext.data(), ciphertext.size(), &result,
1033 &input_consumed));
Shawn Willden4200f212014-12-02 07:01:21 -07001034 EXPECT_EQ(KM_ERROR_UNKNOWN_ERROR, FinishOperation(op_handle, &result));
1035 EXPECT_EQ(0, result.size());
1036}
1037
1038TEST_F(EncryptionOperationsTest, RsaPkcs1Success) {
1039 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_PKCS1_1_5_ENCRYPT, 512);
1040 const char message[] = "Hello World!";
Shawn Willden6dde87c2014-12-11 14:08:48 -07001041 string ciphertext1 = EncryptMessage(string(message));
Shawn Willden4200f212014-12-02 07:01:21 -07001042 EXPECT_EQ(512 / 8, ciphertext1.size());
1043
Shawn Willden6dde87c2014-12-11 14:08:48 -07001044 string ciphertext2 = EncryptMessage(string(message));
Shawn Willden4200f212014-12-02 07:01:21 -07001045 EXPECT_EQ(512 / 8, ciphertext2.size());
1046
1047 // PKCS1 v1.5 randomizes padding so every result should be different.
1048 EXPECT_NE(ciphertext1, ciphertext2);
1049}
1050
1051TEST_F(EncryptionOperationsTest, RsaPkcs1RoundTrip) {
1052 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_PKCS1_1_5_ENCRYPT, 512);
1053 const char message[] = "Hello World!";
Shawn Willden6dde87c2014-12-11 14:08:48 -07001054 string ciphertext = EncryptMessage(string(message));
Shawn Willden4200f212014-12-02 07:01:21 -07001055 EXPECT_EQ(512 / 8, ciphertext.size());
1056
Shawn Willden6dde87c2014-12-11 14:08:48 -07001057 string plaintext = DecryptMessage(ciphertext);
Shawn Willden4200f212014-12-02 07:01:21 -07001058 EXPECT_EQ(message, plaintext);
1059}
1060
1061TEST_F(EncryptionOperationsTest, RsaPkcs1TooLarge) {
1062 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_PKCS1_1_5_ENCRYPT, 512);
1063 const char message[] = "1234567890123456789012345678901234567890123456789012";
1064 uint64_t op_handle;
1065 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -07001066 size_t input_consumed;
Shawn Willden4200f212014-12-02 07:01:21 -07001067
Shawn Willden5b53c992015-02-02 08:05:25 -07001068 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_ENCRYPT, blob_, &op_handle));
Shawn Willdenb7361132014-12-08 08:15:14 -07001069 EXPECT_EQ(KM_ERROR_OK,
1070 UpdateOperation(op_handle, message, array_size(message), &result, &input_consumed));
Shawn Willden4200f212014-12-02 07:01:21 -07001071 EXPECT_EQ(KM_ERROR_INVALID_INPUT_LENGTH, FinishOperation(op_handle, &result));
1072 EXPECT_EQ(0, result.size());
1073}
1074
1075TEST_F(EncryptionOperationsTest, RsaPkcs1CorruptedDecrypt) {
1076 GenerateKey(KM_ALGORITHM_RSA, KM_PAD_RSA_PKCS1_1_5_ENCRYPT, 512);
1077 const char message[] = "Hello World!";
Shawn Willden6dde87c2014-12-11 14:08:48 -07001078 string ciphertext = EncryptMessage(string(message));
Shawn Willden4200f212014-12-02 07:01:21 -07001079 EXPECT_EQ(512 / 8, ciphertext.size());
1080
1081 // Corrupt the ciphertext
1082 ciphertext[512 / 8 / 2]++;
1083
1084 uint64_t op_handle;
1085 string result;
Shawn Willdenb7361132014-12-08 08:15:14 -07001086 size_t input_consumed;
Shawn Willden5b53c992015-02-02 08:05:25 -07001087 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_DECRYPT, blob_, &op_handle));
Shawn Willdenb7361132014-12-08 08:15:14 -07001088 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, ciphertext.data(), ciphertext.size(), &result,
1089 &input_consumed));
Shawn Willden4200f212014-12-02 07:01:21 -07001090 EXPECT_EQ(KM_ERROR_UNKNOWN_ERROR, FinishOperation(op_handle, &result));
1091 EXPECT_EQ(0, result.size());
1092}
1093
Shawn Willden907c3012014-12-08 15:51:55 -07001094TEST_F(EncryptionOperationsTest, AesOcbSuccess) {
1095 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1096 const char message[] = "Hello World!";
Shawn Willden6dde87c2014-12-11 14:08:48 -07001097 string ciphertext1 = EncryptMessage(string(message));
Shawn Willden907c3012014-12-08 15:51:55 -07001098 EXPECT_EQ(12 /* nonce */ + strlen(message) + 16 /* tag */, ciphertext1.size());
1099
Shawn Willden6dde87c2014-12-11 14:08:48 -07001100 string ciphertext2 = EncryptMessage(string(message));
Shawn Willden907c3012014-12-08 15:51:55 -07001101 EXPECT_EQ(12 /* nonce */ + strlen(message) + 16 /* tag */, ciphertext2.size());
1102
1103 // OCB uses a random nonce, so every output should be different
1104 EXPECT_NE(ciphertext1, ciphertext2);
1105}
1106
Shawn Willden6dde87c2014-12-11 14:08:48 -07001107TEST_F(EncryptionOperationsTest, AesOcbRoundTripSuccess) {
1108 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1109 string message = "Hello World!";
1110 string ciphertext = EncryptMessage(message);
1111 EXPECT_EQ(12 /* nonce */ + message.length() + 16 /* tag */, ciphertext.size());
1112
1113 string plaintext = DecryptMessage(ciphertext);
1114 EXPECT_EQ(message, plaintext);
1115}
1116
1117TEST_F(EncryptionOperationsTest, AesOcbRoundTripCorrupted) {
1118 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1119 const char message[] = "Hello World!";
1120 string ciphertext = EncryptMessage(string(message));
1121 EXPECT_EQ(12 /* nonce */ + strlen(message) + 16 /* tag */, ciphertext.size());
1122
1123 ciphertext[ciphertext.size() / 2]++;
1124
1125 uint64_t op_handle;
1126 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_DECRYPT, key_blob(), &op_handle));
1127
1128 string result;
1129 size_t input_consumed;
1130 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, ciphertext.c_str(), ciphertext.length(),
1131 &result, &input_consumed));
1132 EXPECT_EQ(ciphertext.length(), input_consumed);
1133 EXPECT_EQ(KM_ERROR_VERIFICATION_FAILED, FinishOperation(op_handle, &result));
1134}
1135
1136TEST_F(EncryptionOperationsTest, AesDecryptGarbage) {
1137 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1138 string ciphertext(128, 'a');
1139 uint64_t op_handle;
1140 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_DECRYPT, key_blob(), &op_handle));
1141
1142 string result;
1143 size_t input_consumed;
1144 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, ciphertext.c_str(), ciphertext.length(),
1145 &result, &input_consumed));
1146 EXPECT_EQ(ciphertext.length(), input_consumed);
1147 EXPECT_EQ(KM_ERROR_VERIFICATION_FAILED, FinishOperation(op_handle, &result));
1148}
1149
1150TEST_F(EncryptionOperationsTest, AesDecryptTooShort) {
1151 // Try decrypting garbage ciphertext that is too short to be valid (< nonce + tag).
1152 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1153 string ciphertext(12 + 15, 'a');
1154 uint64_t op_handle;
1155 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_DECRYPT, key_blob(), &op_handle));
1156
1157 string result;
1158 size_t input_consumed;
1159 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, ciphertext.c_str(), ciphertext.length(),
1160 &result, &input_consumed));
1161 EXPECT_EQ(ciphertext.length(), input_consumed);
1162 EXPECT_EQ(KM_ERROR_INVALID_INPUT_LENGTH, FinishOperation(op_handle, &result));
1163}
1164
1165TEST_F(EncryptionOperationsTest, AesOcbRoundTripEmptySuccess) {
1166 // Empty messages should work fine.
1167 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1168 const char message[] = "";
1169 string ciphertext = EncryptMessage(string(message));
1170 EXPECT_EQ(12 /* nonce */ + strlen(message) + 16 /* tag */, ciphertext.size());
1171
1172 string plaintext = DecryptMessage(ciphertext);
1173 EXPECT_EQ(message, plaintext);
1174}
1175
1176TEST_F(EncryptionOperationsTest, AesOcbRoundTripEmptyCorrupted) {
1177 // Should even detect corruption of empty messages.
1178 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1179 const char message[] = "";
1180 string ciphertext = EncryptMessage(string(message));
1181 EXPECT_EQ(12 /* nonce */ + strlen(message) + 16 /* tag */, ciphertext.size());
1182
1183 ciphertext[ciphertext.size() / 2]++;
1184
1185 uint64_t op_handle;
1186 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_DECRYPT, key_blob(), &op_handle));
1187
1188 string result;
1189 size_t input_consumed;
1190 EXPECT_EQ(KM_ERROR_OK, UpdateOperation(op_handle, ciphertext.c_str(), ciphertext.length(),
1191 &result, &input_consumed));
1192 EXPECT_EQ(ciphertext.length(), input_consumed);
1193 EXPECT_EQ(KM_ERROR_VERIFICATION_FAILED, FinishOperation(op_handle, &result));
1194}
1195
1196TEST_F(EncryptionOperationsTest, AesOcbFullChunk) {
1197 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1198 string message(4096, 'a');
1199 string ciphertext = EncryptMessage(message);
1200 EXPECT_EQ(12 /* nonce */ + message.length() + 16 /* tag */, ciphertext.size());
1201
1202 string plaintext = DecryptMessage(ciphertext);
1203 EXPECT_EQ(message, plaintext);
1204}
1205
1206TEST_F(EncryptionOperationsTest, AesOcbVariousChunkLengths) {
1207 for (unsigned chunk_length = 1; chunk_length <= 128; ++chunk_length) {
1208 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, chunk_length);
1209 string message(128, 'a');
1210 string ciphertext = EncryptMessage(message);
1211 int expected_tag_count = (message.length() + chunk_length - 1) / chunk_length;
1212 EXPECT_EQ(12 /* nonce */ + message.length() + 16 * expected_tag_count, ciphertext.size())
1213 << "Unexpected ciphertext size for chunk length " << chunk_length
1214 << " expected tag count was " << expected_tag_count
1215 << " but actual tag count was probably "
1216 << (ciphertext.size() - message.length() - 12) / 16;
1217
1218 string plaintext = DecryptMessage(ciphertext);
1219 EXPECT_EQ(message, plaintext);
1220 }
1221}
1222
1223TEST_F(EncryptionOperationsTest, AesOcbAbort) {
1224 GenerateSymmetricKey(KM_ALGORITHM_AES, 128, KM_MODE_OCB, 4096);
1225 const char message[] = "Hello";
1226
1227 uint64_t op_handle;
1228 EXPECT_EQ(KM_ERROR_OK, BeginOperation(KM_PURPOSE_ENCRYPT, key_blob(), &op_handle));
1229
1230 string result;
1231 size_t input_consumed;
1232 EXPECT_EQ(KM_ERROR_OK,
1233 UpdateOperation(op_handle, message, strlen(message), &result, &input_consumed));
1234 EXPECT_EQ(strlen(message), input_consumed);
1235 EXPECT_EQ(KM_ERROR_OK, device()->abort(device(), op_handle));
1236}
1237
Shawn Willdenbe4a2a32014-12-15 14:51:10 -07001238TEST_F(EncryptionOperationsTest, AesOcbNoChunkLength) {
1239 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
1240 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT));
1241 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES));
1242 params_.push_back(Authorization(TAG_KEY_SIZE, 128));
1243 params_.push_back(Authorization(TAG_MAC_LENGTH, 16));
1244 params_.push_back(Authorization(TAG_BLOCK_MODE, KM_MODE_OCB));
1245 params_.push_back(Authorization(TAG_PADDING, KM_PAD_NONE));
1246
1247 GenerateKey(&params_);
1248 uint64_t op_handle;
1249 EXPECT_EQ(KM_ERROR_INVALID_ARGUMENT,
1250 BeginOperation(KM_PURPOSE_ENCRYPT, key_blob(), &op_handle));
1251}
1252
1253TEST_F(EncryptionOperationsTest, AesEcbUnsupported) {
1254 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
1255 params_.push_back(Authorization(TAG_MAC_LENGTH, 16));
1256 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT));
1257 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES));
1258 params_.push_back(Authorization(TAG_KEY_SIZE, 128));
1259 params_.push_back(Authorization(TAG_BLOCK_MODE, KM_MODE_ECB));
1260 params_.push_back(Authorization(TAG_PADDING, KM_PAD_NONE));
1261
1262 GenerateKey(&params_);
1263 uint64_t op_handle;
1264 EXPECT_EQ(KM_ERROR_UNSUPPORTED_BLOCK_MODE,
1265 BeginOperation(KM_PURPOSE_ENCRYPT, key_blob(), &op_handle));
1266}
1267
1268TEST_F(EncryptionOperationsTest, AesOcbPaddingUnsupported) {
1269 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
1270 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT));
1271 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES));
1272 params_.push_back(Authorization(TAG_KEY_SIZE, 128));
1273 params_.push_back(Authorization(TAG_MAC_LENGTH, 16));
1274 params_.push_back(Authorization(TAG_BLOCK_MODE, KM_MODE_OCB));
1275 params_.push_back(Authorization(TAG_CHUNK_LENGTH, 4096));
1276 params_.push_back(Authorization(TAG_PADDING, KM_PAD_ZERO));
1277
1278 GenerateKey(&params_);
1279 uint64_t op_handle;
1280 EXPECT_EQ(KM_ERROR_UNSUPPORTED_PADDING_MODE,
1281 BeginOperation(KM_PURPOSE_ENCRYPT, key_blob(), &op_handle));
1282}
1283
1284TEST_F(EncryptionOperationsTest, AesOcbInvalidMacLength) {
1285 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_ENCRYPT));
1286 params_.push_back(Authorization(TAG_PURPOSE, KM_PURPOSE_DECRYPT));
1287 params_.push_back(Authorization(TAG_ALGORITHM, KM_ALGORITHM_AES));
1288 params_.push_back(Authorization(TAG_KEY_SIZE, 128));
1289 params_.push_back(Authorization(TAG_MAC_LENGTH, 17));
1290 params_.push_back(Authorization(TAG_BLOCK_MODE, KM_MODE_OCB));
1291 params_.push_back(Authorization(TAG_CHUNK_LENGTH, 4096));
1292
1293 GenerateKey(&params_);
1294 uint64_t op_handle;
1295 EXPECT_EQ(KM_ERROR_INVALID_KEY_BLOB,
1296 BeginOperation(KM_PURPOSE_ENCRYPT, key_blob(), &op_handle));
1297}
1298
Shawn Willden128ffe02014-08-06 12:31:33 -06001299} // namespace test
1300} // namespace keymaster