1 /* 2 * Copyright 2013 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package android.keystore.cts; 18 19 import android.security.KeyPairGeneratorSpec; 20 import android.security.keystore.KeyGenParameterSpec; 21 import android.security.keystore.KeyInfo; 22 import android.security.keystore.KeyProperties; 23 import android.test.AndroidTestCase; 24 import android.test.MoreAsserts; 25 26 import java.math.BigInteger; 27 import java.net.InetAddress; 28 import java.net.Socket; 29 import java.security.InvalidAlgorithmParameterException; 30 import java.security.KeyPair; 31 import java.security.KeyPairGenerator; 32 import java.security.KeyStore; 33 import java.security.NoSuchAlgorithmException; 34 import java.security.NoSuchProviderException; 35 import java.security.Principal; 36 import java.security.PrivateKey; 37 import java.security.Provider; 38 import java.security.SecureRandom; 39 import java.security.Security; 40 import java.security.Provider.Service; 41 import java.security.cert.Certificate; 42 import java.security.cert.X509Certificate; 43 import java.security.interfaces.ECKey; 44 import java.security.interfaces.ECPublicKey; 45 import java.security.interfaces.RSAPublicKey; 46 import java.security.spec.AlgorithmParameterSpec; 47 import java.security.spec.ECGenParameterSpec; 48 import java.security.spec.ECParameterSpec; 49 import java.security.spec.RSAKeyGenParameterSpec; 50 import java.text.SimpleDateFormat; 51 import java.util.ArrayList; 52 import java.util.Arrays; 53 import java.util.Date; 54 import java.util.HashSet; 55 import java.util.List; 56 import java.util.Locale; 57 import java.util.Map; 58 import java.util.Set; 59 import java.util.TreeMap; 60 import java.util.concurrent.Callable; 61 import java.util.concurrent.ExecutorService; 62 import java.util.concurrent.Executors; 63 import java.util.concurrent.Future; 64 import java.text.DecimalFormatSymbols; 65 66 import javax.net.ssl.KeyManager; 67 import javax.net.ssl.SSLContext; 68 import javax.net.ssl.SSLServerSocket; 69 import javax.net.ssl.SSLSocket; 70 import javax.net.ssl.X509ExtendedKeyManager; 71 import javax.security.auth.x500.X500Principal; 72 73 import libcore.java.security.TestKeyStore; 74 import libcore.javax.net.ssl.TestKeyManager; 75 import libcore.javax.net.ssl.TestSSLContext; 76 77 public class KeyPairGeneratorTest extends AndroidTestCase { 78 private KeyStore mKeyStore; 79 80 private CountingSecureRandom mRng; 81 82 private static final String TEST_ALIAS_1 = "test1"; 83 84 private static final String TEST_ALIAS_2 = "test2"; 85 86 private static final String TEST_ALIAS_3 = "test3"; 87 88 private static final X500Principal TEST_DN_1 = new X500Principal("CN=test1"); 89 90 private static final X500Principal TEST_DN_2 = new X500Principal("CN=test2"); 91 92 private static final BigInteger TEST_SERIAL_1 = BigInteger.ONE; 93 94 private static final BigInteger TEST_SERIAL_2 = BigInteger.valueOf(2L); 95 96 private static final long NOW_MILLIS = System.currentTimeMillis(); 97 98 /* We have to round this off because X509v3 doesn't store milliseconds. */ 99 private static final Date NOW = new Date(NOW_MILLIS - (NOW_MILLIS % 1000L)); 100 101 @SuppressWarnings("deprecation") 102 private static final Date NOW_PLUS_10_YEARS = new Date(NOW.getYear() + 10, 0, 1); 103 104 private static final long DAY_IN_MILLIS = 1000 * 60 * 60 * 24; 105 106 private static final X500Principal DEFAULT_CERT_SUBJECT = new X500Principal("CN=fake"); 107 private static final BigInteger DEFAULT_CERT_SERIAL_NUMBER = new BigInteger("1"); 108 private static final Date DEFAULT_CERT_NOT_BEFORE = new Date(0L); // Jan 1 1970 109 private static final Date DEFAULT_CERT_NOT_AFTER = new Date(2461449600000L); // Jan 1 2048 110 111 private static final String EXPECTED_PROVIDER_NAME = TestUtils.EXPECTED_PROVIDER_NAME; 112 113 private static final String[] EXPECTED_ALGORITHMS = { 114 "EC", 115 "RSA", 116 }; 117 118 private static final Map<String, Integer> DEFAULT_KEY_SIZES = 119 new TreeMap<>(String.CASE_INSENSITIVE_ORDER); 120 static { 121 DEFAULT_KEY_SIZES.put("EC", 256); 122 DEFAULT_KEY_SIZES.put("RSA", 2048); 123 } 124 125 @Override setUp()126 protected void setUp() throws Exception { 127 super.setUp(); 128 mRng = new CountingSecureRandom(); 129 mKeyStore = KeyStore.getInstance("AndroidKeyStore"); 130 mKeyStore.load(null, null); 131 } 132 testAlgorithmList()133 public void testAlgorithmList() { 134 // Assert that Android Keystore Provider exposes exactly the expected KeyPairGenerator 135 // algorithms. We don't care whether the algorithms are exposed via aliases, as long as 136 // canonical names of algorithms are accepted. If the Provider exposes extraneous 137 // algorithms, it'll be caught because it'll have to expose at least one Service for such an 138 // algorithm, and this Service's algorithm will not be in the expected set. 139 140 Provider provider = Security.getProvider(EXPECTED_PROVIDER_NAME); 141 Set<Service> services = provider.getServices(); 142 Set<String> actualAlgsLowerCase = new HashSet<String>(); 143 Set<String> expectedAlgsLowerCase = new HashSet<String>( 144 Arrays.asList(TestUtils.toLowerCase(EXPECTED_ALGORITHMS))); 145 for (Service service : services) { 146 if ("KeyPairGenerator".equalsIgnoreCase(service.getType())) { 147 String algLowerCase = service.getAlgorithm().toLowerCase(Locale.US); 148 actualAlgsLowerCase.add(algLowerCase); 149 } 150 } 151 152 TestUtils.assertContentsInAnyOrder(actualAlgsLowerCase, 153 expectedAlgsLowerCase.toArray(new String[0])); 154 } 155 testInitialize_LegacySpec()156 public void testInitialize_LegacySpec() throws Exception { 157 @SuppressWarnings("deprecation") 158 KeyPairGeneratorSpec spec = new KeyPairGeneratorSpec.Builder(getContext()) 159 .setAlias(TEST_ALIAS_1) 160 .setSubject(TEST_DN_1) 161 .setSerialNumber(TEST_SERIAL_1) 162 .setStartDate(NOW) 163 .setEndDate(NOW_PLUS_10_YEARS) 164 .build(); 165 getRsaGenerator().initialize(spec); 166 getRsaGenerator().initialize(spec, new SecureRandom()); 167 168 getEcGenerator().initialize(spec); 169 getEcGenerator().initialize(spec, new SecureRandom()); 170 } 171 testInitialize_ModernSpec()172 public void testInitialize_ModernSpec() throws Exception { 173 KeyGenParameterSpec spec = new KeyGenParameterSpec.Builder( 174 TEST_ALIAS_1, 175 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 176 .build(); 177 getRsaGenerator().initialize(spec); 178 getRsaGenerator().initialize(spec, new SecureRandom()); 179 180 getEcGenerator().initialize(spec); 181 getEcGenerator().initialize(spec, new SecureRandom()); 182 } 183 testInitialize_KeySizeOnly()184 public void testInitialize_KeySizeOnly() throws Exception { 185 try { 186 getRsaGenerator().initialize(1024); 187 fail("KeyPairGenerator should not support setting the key size"); 188 } catch (IllegalArgumentException success) { 189 } 190 191 try { 192 getEcGenerator().initialize(256); 193 fail("KeyPairGenerator should not support setting the key size"); 194 } catch (IllegalArgumentException success) { 195 } 196 } 197 testInitialize_KeySizeAndSecureRandomOnly()198 public void testInitialize_KeySizeAndSecureRandomOnly() 199 throws Exception { 200 try { 201 getRsaGenerator().initialize(1024, new SecureRandom()); 202 fail("KeyPairGenerator should not support setting the key size"); 203 } catch (IllegalArgumentException success) { 204 } 205 206 try { 207 getEcGenerator().initialize(1024, new SecureRandom()); 208 fail("KeyPairGenerator should not support setting the key size"); 209 } catch (IllegalArgumentException success) { 210 } 211 } 212 testDefaultKeySize()213 public void testDefaultKeySize() throws Exception { 214 for (String algorithm : EXPECTED_ALGORITHMS) { 215 try { 216 int expectedSizeBits = DEFAULT_KEY_SIZES.get(algorithm); 217 KeyPairGenerator generator = getGenerator(algorithm); 218 generator.initialize(getWorkingSpec().build()); 219 KeyPair keyPair = generator.generateKeyPair(); 220 assertEquals(expectedSizeBits, 221 TestUtils.getKeyInfo(keyPair.getPrivate()).getKeySize()); 222 } catch (Throwable e) { 223 throw new RuntimeException("Failed for " + algorithm, e); 224 } 225 } 226 } 227 testInitWithUnknownBlockModeFails()228 public void testInitWithUnknownBlockModeFails() { 229 for (String algorithm : EXPECTED_ALGORITHMS) { 230 try { 231 KeyPairGenerator generator = getGenerator(algorithm); 232 try { 233 generator.initialize(getWorkingSpec().setBlockModes("weird").build()); 234 fail(); 235 } catch (InvalidAlgorithmParameterException expected) {} 236 } catch (Throwable e) { 237 throw new RuntimeException("Failed for " + algorithm, e); 238 } 239 } 240 } 241 testInitWithUnknownEncryptionPaddingFails()242 public void testInitWithUnknownEncryptionPaddingFails() { 243 for (String algorithm : EXPECTED_ALGORITHMS) { 244 try { 245 KeyPairGenerator generator = getGenerator(algorithm); 246 try { 247 generator.initialize(getWorkingSpec().setEncryptionPaddings("weird").build()); 248 fail(); 249 } catch (InvalidAlgorithmParameterException expected) {} 250 } catch (Throwable e) { 251 throw new RuntimeException("Failed for " + algorithm, e); 252 } 253 } 254 } 255 testInitWithUnknownSignaturePaddingFails()256 public void testInitWithUnknownSignaturePaddingFails() { 257 for (String algorithm : EXPECTED_ALGORITHMS) { 258 try { 259 KeyPairGenerator generator = getGenerator(algorithm); 260 try { 261 generator.initialize(getWorkingSpec().setSignaturePaddings("weird").build()); 262 fail(); 263 } catch (InvalidAlgorithmParameterException expected) {} 264 } catch (Throwable e) { 265 throw new RuntimeException("Failed for " + algorithm, e); 266 } 267 } 268 } 269 testInitWithUnknownDigestFails()270 public void testInitWithUnknownDigestFails() { 271 for (String algorithm : EXPECTED_ALGORITHMS) { 272 try { 273 KeyPairGenerator generator = getGenerator(algorithm); 274 try { 275 generator.initialize(getWorkingSpec().setDigests("weird").build()); 276 fail(); 277 } catch (InvalidAlgorithmParameterException expected) {} 278 } catch (Throwable e) { 279 throw new RuntimeException("Failed for " + algorithm, e); 280 } 281 } 282 } 283 testInitRandomizedEncryptionRequiredButViolatedFails()284 public void testInitRandomizedEncryptionRequiredButViolatedFails() throws Exception { 285 for (String algorithm : EXPECTED_ALGORITHMS) { 286 try { 287 KeyPairGenerator generator = getGenerator(algorithm); 288 try { 289 generator.initialize(getWorkingSpec( 290 KeyProperties.PURPOSE_ENCRYPT) 291 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_NONE) 292 .build()); 293 fail(); 294 } catch (InvalidAlgorithmParameterException expected) {} 295 } catch (Throwable e) { 296 throw new RuntimeException("Failed for " + algorithm, e); 297 } 298 } 299 } 300 testGenerateHonorsRequestedAuthorizations()301 public void testGenerateHonorsRequestedAuthorizations() throws Exception { 302 Date keyValidityStart = new Date(System.currentTimeMillis() - TestUtils.DAY_IN_MILLIS); 303 Date keyValidityForOriginationEnd = 304 new Date(System.currentTimeMillis() + TestUtils.DAY_IN_MILLIS); 305 Date keyValidityForConsumptionEnd = 306 new Date(System.currentTimeMillis() + 3 * TestUtils.DAY_IN_MILLIS); 307 for (String algorithm : EXPECTED_ALGORITHMS) { 308 try { 309 String[] blockModes = 310 new String[] {KeyProperties.BLOCK_MODE_GCM, KeyProperties.BLOCK_MODE_CBC}; 311 String[] encryptionPaddings = 312 new String[] {KeyProperties.ENCRYPTION_PADDING_RSA_OAEP, 313 KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1}; 314 String[] digests = 315 new String[] {KeyProperties.DIGEST_SHA256, KeyProperties.DIGEST_SHA1}; 316 int purposes = KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_ENCRYPT; 317 KeyPairGenerator generator = getGenerator(algorithm); 318 generator.initialize(getWorkingSpec(purposes) 319 .setBlockModes(blockModes) 320 .setEncryptionPaddings(encryptionPaddings) 321 .setDigests(digests) 322 .setKeyValidityStart(keyValidityStart) 323 .setKeyValidityForOriginationEnd(keyValidityForOriginationEnd) 324 .setKeyValidityForConsumptionEnd(keyValidityForConsumptionEnd) 325 .build()); 326 KeyPair keyPair = generator.generateKeyPair(); 327 assertEquals(algorithm, keyPair.getPrivate().getAlgorithm()); 328 329 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 330 assertEquals(purposes, keyInfo.getPurposes()); 331 TestUtils.assertContentsInAnyOrder( 332 Arrays.asList(keyInfo.getBlockModes()), blockModes); 333 334 List<String> actualEncryptionPaddings = 335 new ArrayList<String>(Arrays.asList(keyInfo.getEncryptionPaddings())); 336 // Keystore may have added ENCRYPTION_PADDING_NONE to allow software OAEP 337 actualEncryptionPaddings.remove(KeyProperties.ENCRYPTION_PADDING_NONE); 338 TestUtils.assertContentsInAnyOrder( 339 actualEncryptionPaddings, encryptionPaddings); 340 341 List<String> actualDigests = 342 new ArrayList<String>(Arrays.asList(keyInfo.getDigests())); 343 // Keystore may have added DIGEST_NONE, to allow software digesting. 344 actualDigests.remove(KeyProperties.DIGEST_NONE); 345 TestUtils.assertContentsInAnyOrder(actualDigests, digests); 346 347 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getSignaturePaddings())); 348 assertEquals(keyValidityStart, keyInfo.getKeyValidityStart()); 349 assertEquals(keyValidityForOriginationEnd, 350 keyInfo.getKeyValidityForOriginationEnd()); 351 assertEquals(keyValidityForConsumptionEnd, 352 keyInfo.getKeyValidityForConsumptionEnd()); 353 assertFalse(keyInfo.isUserAuthenticationRequired()); 354 assertFalse(keyInfo.isUserAuthenticationRequirementEnforcedBySecureHardware()); 355 } catch (Throwable e) { 356 throw new RuntimeException("Failed for " + algorithm, e); 357 } 358 } 359 } 360 361 @SuppressWarnings("deprecation") testGenerate_EC_LegacySpec()362 public void testGenerate_EC_LegacySpec() throws Exception { 363 // There are three legacy ways to generate an EC key pair using Android Keystore 364 // KeyPairGenerator: 365 // 1. Use an RSA KeyPairGenerator and specify EC as key type, 366 // 2. Use an EC KeyPairGenerator and specify EC as key type, 367 // 3. Use an EC KeyPairGenerator and leave the key type unspecified. 368 // 369 // We test all three. 370 371 // 1. Use an RSA KeyPairGenerator and specify EC as key type. 372 KeyPairGenerator generator = getRsaGenerator(); 373 generator.initialize(new KeyPairGeneratorSpec.Builder(getContext()) 374 .setAlias(TEST_ALIAS_1) 375 .setKeyType("EC") 376 .setSubject(TEST_DN_1) 377 .setSerialNumber(TEST_SERIAL_1) 378 .setStartDate(NOW) 379 .setEndDate(NOW_PLUS_10_YEARS) 380 .build()); 381 KeyPair keyPair = generator.generateKeyPair(); 382 assertGeneratedKeyPairAndSelfSignedCertificate( 383 keyPair, 384 TEST_ALIAS_1, 385 "EC", 386 256, 387 TEST_DN_1, 388 TEST_SERIAL_1, NOW, 389 NOW_PLUS_10_YEARS); 390 assertSelfSignedCertificateSignatureVerifies(TEST_ALIAS_1); 391 assertKeyPairAndCertificateUsableForTLSPeerAuthentication(TEST_ALIAS_1); 392 TestUtils.assertECParameterSpecEqualsIgnoreSeedIfNotPresent( 393 ECCurves.NIST_P_256_SPEC, ((ECPublicKey) keyPair.getPublic()).getParams()); 394 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 395 assertEquals(256, keyInfo.getKeySize()); 396 assertEquals(TEST_ALIAS_1, keyInfo.getKeystoreAlias()); 397 assertOneOf(keyInfo.getOrigin(), 398 KeyProperties.ORIGIN_GENERATED, KeyProperties.ORIGIN_UNKNOWN); 399 assertEquals( 400 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY, 401 keyInfo.getPurposes()); 402 assertFalse(keyInfo.isUserAuthenticationRequired()); 403 assertEquals(null, keyInfo.getKeyValidityStart()); 404 assertEquals(null, keyInfo.getKeyValidityForOriginationEnd()); 405 assertEquals(null, keyInfo.getKeyValidityForConsumptionEnd()); 406 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 407 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getDigests()), 408 KeyProperties.DIGEST_NONE, 409 KeyProperties.DIGEST_SHA1, 410 KeyProperties.DIGEST_SHA224, 411 KeyProperties.DIGEST_SHA256, 412 KeyProperties.DIGEST_SHA384, 413 KeyProperties.DIGEST_SHA512); 414 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getSignaturePaddings())); 415 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getEncryptionPaddings())); 416 417 // 2. Use an EC KeyPairGenerator and specify EC as key type. 418 generator = getEcGenerator(); 419 generator.initialize(new KeyPairGeneratorSpec.Builder(getContext()) 420 .setAlias(TEST_ALIAS_2) 421 .setKeyType("EC") 422 .setSubject(TEST_DN_1) 423 .setSerialNumber(TEST_SERIAL_1) 424 .setStartDate(NOW) 425 .setEndDate(NOW_PLUS_10_YEARS) 426 .build()); 427 keyPair = generator.generateKeyPair(); 428 assertGeneratedKeyPairAndSelfSignedCertificate( 429 keyPair, 430 TEST_ALIAS_2, 431 "EC", 432 256, 433 TEST_DN_1, 434 TEST_SERIAL_1, 435 NOW, 436 NOW_PLUS_10_YEARS); 437 assertSelfSignedCertificateSignatureVerifies(TEST_ALIAS_2); 438 assertKeyPairAndCertificateUsableForTLSPeerAuthentication(TEST_ALIAS_2); 439 TestUtils.assertECParameterSpecEqualsIgnoreSeedIfNotPresent( 440 ECCurves.NIST_P_256_SPEC, ((ECPublicKey) keyPair.getPublic()).getParams()); 441 keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 442 assertEquals(256, keyInfo.getKeySize()); 443 assertEquals(TEST_ALIAS_2, keyInfo.getKeystoreAlias()); 444 assertOneOf(keyInfo.getOrigin(), 445 KeyProperties.ORIGIN_GENERATED, KeyProperties.ORIGIN_UNKNOWN); 446 assertEquals( 447 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY, 448 keyInfo.getPurposes()); 449 assertFalse(keyInfo.isUserAuthenticationRequired()); 450 assertEquals(null, keyInfo.getKeyValidityStart()); 451 assertEquals(null, keyInfo.getKeyValidityForOriginationEnd()); 452 assertEquals(null, keyInfo.getKeyValidityForConsumptionEnd()); 453 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 454 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getDigests()), 455 KeyProperties.DIGEST_NONE, 456 KeyProperties.DIGEST_SHA1, 457 KeyProperties.DIGEST_SHA224, 458 KeyProperties.DIGEST_SHA256, 459 KeyProperties.DIGEST_SHA384, 460 KeyProperties.DIGEST_SHA512); 461 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getSignaturePaddings())); 462 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getEncryptionPaddings())); 463 464 // 3. Use an EC KeyPairGenerator and leave the key type unspecified. 465 generator = getEcGenerator(); 466 generator.initialize(new KeyPairGeneratorSpec.Builder(getContext()) 467 .setAlias(TEST_ALIAS_3) 468 .setSubject(TEST_DN_1) 469 .setSerialNumber(TEST_SERIAL_1) 470 .setStartDate(NOW) 471 .setEndDate(NOW_PLUS_10_YEARS) 472 .build()); 473 keyPair = generator.generateKeyPair(); 474 assertGeneratedKeyPairAndSelfSignedCertificate( 475 keyPair, 476 TEST_ALIAS_3, 477 "EC", 478 256, 479 TEST_DN_1, 480 TEST_SERIAL_1, 481 NOW, 482 NOW_PLUS_10_YEARS); 483 assertSelfSignedCertificateSignatureVerifies(TEST_ALIAS_3); 484 assertKeyPairAndCertificateUsableForTLSPeerAuthentication(TEST_ALIAS_3); 485 TestUtils.assertECParameterSpecEqualsIgnoreSeedIfNotPresent( 486 ECCurves.NIST_P_256_SPEC, ((ECPublicKey) keyPair.getPublic()).getParams()); 487 keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 488 assertEquals(256, keyInfo.getKeySize()); 489 assertEquals(TEST_ALIAS_3, keyInfo.getKeystoreAlias()); 490 assertOneOf(keyInfo.getOrigin(), 491 KeyProperties.ORIGIN_GENERATED, KeyProperties.ORIGIN_UNKNOWN); 492 assertEquals( 493 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY, 494 keyInfo.getPurposes()); 495 assertFalse(keyInfo.isUserAuthenticationRequired()); 496 assertEquals(null, keyInfo.getKeyValidityStart()); 497 assertEquals(null, keyInfo.getKeyValidityForOriginationEnd()); 498 assertEquals(null, keyInfo.getKeyValidityForConsumptionEnd()); 499 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 500 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getDigests()), 501 KeyProperties.DIGEST_NONE, 502 KeyProperties.DIGEST_SHA1, 503 KeyProperties.DIGEST_SHA224, 504 KeyProperties.DIGEST_SHA256, 505 KeyProperties.DIGEST_SHA384, 506 KeyProperties.DIGEST_SHA512); 507 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getSignaturePaddings())); 508 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getEncryptionPaddings())); 509 } 510 testGenerate_RSA_LegacySpec()511 public void testGenerate_RSA_LegacySpec() throws Exception { 512 KeyPairGenerator generator = getRsaGenerator(); 513 generator.initialize(new KeyPairGeneratorSpec.Builder(getContext()) 514 .setAlias(TEST_ALIAS_1) 515 .setSubject(TEST_DN_1) 516 .setSerialNumber(TEST_SERIAL_1) 517 .setStartDate(NOW) 518 .setEndDate(NOW_PLUS_10_YEARS) 519 .build()); 520 KeyPair keyPair = generator.generateKeyPair(); 521 assertGeneratedKeyPairAndSelfSignedCertificate( 522 keyPair, 523 TEST_ALIAS_1, 524 "RSA", 525 2048, 526 TEST_DN_1, 527 TEST_SERIAL_1, 528 NOW, 529 NOW_PLUS_10_YEARS); 530 assertSelfSignedCertificateSignatureVerifies(TEST_ALIAS_1); 531 assertKeyPairAndCertificateUsableForTLSPeerAuthentication(TEST_ALIAS_1); 532 assertEquals(RSAKeyGenParameterSpec.F4, 533 ((RSAPublicKey) keyPair.getPublic()).getPublicExponent()); 534 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 535 assertEquals(2048, keyInfo.getKeySize()); 536 assertEquals(TEST_ALIAS_1, keyInfo.getKeystoreAlias()); 537 assertOneOf(keyInfo.getOrigin(), 538 KeyProperties.ORIGIN_GENERATED, KeyProperties.ORIGIN_UNKNOWN); 539 assertEquals( 540 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY 541 | KeyProperties.PURPOSE_ENCRYPT | KeyProperties.PURPOSE_DECRYPT, 542 keyInfo.getPurposes()); 543 assertFalse(keyInfo.isUserAuthenticationRequired()); 544 assertEquals(null, keyInfo.getKeyValidityStart()); 545 assertEquals(null, keyInfo.getKeyValidityForOriginationEnd()); 546 assertEquals(null, keyInfo.getKeyValidityForConsumptionEnd()); 547 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 548 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getDigests()), 549 KeyProperties.DIGEST_NONE, 550 KeyProperties.DIGEST_MD5, 551 KeyProperties.DIGEST_SHA1, 552 KeyProperties.DIGEST_SHA224, 553 KeyProperties.DIGEST_SHA256, 554 KeyProperties.DIGEST_SHA384, 555 KeyProperties.DIGEST_SHA512); 556 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getEncryptionPaddings()), 557 KeyProperties.ENCRYPTION_PADDING_NONE, 558 KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1, 559 KeyProperties.ENCRYPTION_PADDING_RSA_OAEP); 560 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getSignaturePaddings()), 561 KeyProperties.SIGNATURE_PADDING_RSA_PSS, 562 KeyProperties.SIGNATURE_PADDING_RSA_PKCS1); 563 } 564 testGenerate_ReplacesOldEntryWithSameAlias()565 public void testGenerate_ReplacesOldEntryWithSameAlias() 566 throws Exception { 567 // Generate the first key 568 { 569 KeyPairGenerator generator = getRsaGenerator(); 570 generator.initialize(new KeyGenParameterSpec.Builder( 571 TEST_ALIAS_1, 572 KeyProperties.PURPOSE_SIGN 573 | KeyProperties.PURPOSE_VERIFY 574 | KeyProperties.PURPOSE_ENCRYPT 575 | KeyProperties.PURPOSE_DECRYPT) 576 .setDigests(KeyProperties.DIGEST_NONE) 577 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1) 578 .setCertificateSubject(TEST_DN_1) 579 .setCertificateSerialNumber(TEST_SERIAL_1) 580 .setCertificateNotBefore(NOW) 581 .setCertificateNotAfter(NOW_PLUS_10_YEARS) 582 .build()); 583 assertGeneratedKeyPairAndSelfSignedCertificate( 584 generator.generateKeyPair(), 585 TEST_ALIAS_1, 586 "RSA", 587 2048, 588 TEST_DN_1, 589 TEST_SERIAL_1, 590 NOW, 591 NOW_PLUS_10_YEARS); 592 } 593 594 // Replace the original key 595 { 596 KeyPairGenerator generator = getRsaGenerator(); 597 generator.initialize(new KeyGenParameterSpec.Builder( 598 TEST_ALIAS_1, 599 KeyProperties.PURPOSE_SIGN 600 | KeyProperties.PURPOSE_VERIFY 601 | KeyProperties.PURPOSE_ENCRYPT 602 | KeyProperties.PURPOSE_DECRYPT) 603 .setDigests(KeyProperties.DIGEST_NONE) 604 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1) 605 .setCertificateSubject(TEST_DN_2) 606 .setCertificateSerialNumber(TEST_SERIAL_2) 607 .setCertificateNotBefore(NOW) 608 .setCertificateNotAfter(NOW_PLUS_10_YEARS) 609 .build()); 610 assertGeneratedKeyPairAndSelfSignedCertificate( 611 generator.generateKeyPair(), 612 TEST_ALIAS_1, 613 "RSA", 614 2048, 615 TEST_DN_2, 616 TEST_SERIAL_2, 617 NOW, 618 NOW_PLUS_10_YEARS); 619 } 620 } 621 testGenerate_DoesNotReplaceOtherEntries()622 public void testGenerate_DoesNotReplaceOtherEntries() 623 throws Exception { 624 // Generate the first key 625 KeyPairGenerator generator = getRsaGenerator(); 626 generator.initialize(new KeyGenParameterSpec.Builder( 627 TEST_ALIAS_1, 628 KeyProperties.PURPOSE_SIGN 629 | KeyProperties.PURPOSE_VERIFY 630 | KeyProperties.PURPOSE_ENCRYPT 631 | KeyProperties.PURPOSE_DECRYPT) 632 .setDigests(KeyProperties.DIGEST_NONE) 633 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1) 634 .setCertificateSubject(TEST_DN_1) 635 .setCertificateSerialNumber(TEST_SERIAL_1) 636 .setCertificateNotBefore(NOW) 637 .setCertificateNotAfter(NOW_PLUS_10_YEARS) 638 .build()); 639 KeyPair keyPair1 = generator.generateKeyPair(); 640 assertGeneratedKeyPairAndSelfSignedCertificate( 641 keyPair1, 642 TEST_ALIAS_1, 643 "RSA", 644 2048, 645 TEST_DN_1, 646 TEST_SERIAL_1, 647 NOW, 648 NOW_PLUS_10_YEARS); 649 650 // Generate the second key 651 generator.initialize(new KeyGenParameterSpec.Builder( 652 TEST_ALIAS_2, 653 KeyProperties.PURPOSE_SIGN 654 | KeyProperties.PURPOSE_VERIFY 655 | KeyProperties.PURPOSE_ENCRYPT 656 | KeyProperties.PURPOSE_DECRYPT) 657 .setDigests(KeyProperties.DIGEST_NONE) 658 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1) 659 .setCertificateSubject(TEST_DN_2) 660 .setCertificateSerialNumber(TEST_SERIAL_2) 661 .setCertificateNotBefore(NOW) 662 .setCertificateNotAfter(NOW_PLUS_10_YEARS) 663 .build()); 664 KeyPair keyPair2 = generator.generateKeyPair(); 665 assertGeneratedKeyPairAndSelfSignedCertificate( 666 keyPair2, 667 TEST_ALIAS_2, 668 "RSA", 669 2048, 670 TEST_DN_2, 671 TEST_SERIAL_2, 672 NOW, 673 NOW_PLUS_10_YEARS); 674 675 // Check the first key pair again 676 assertGeneratedKeyPairAndSelfSignedCertificate( 677 keyPair1, 678 TEST_ALIAS_1, 679 "RSA", 680 2048, 681 TEST_DN_1, 682 TEST_SERIAL_1, 683 NOW, 684 NOW_PLUS_10_YEARS); 685 } 686 testGenerate_EC_ModernSpec_Defaults()687 public void testGenerate_EC_ModernSpec_Defaults() throws Exception { 688 KeyPairGenerator generator = getEcGenerator(); 689 generator.initialize(new KeyGenParameterSpec.Builder( 690 TEST_ALIAS_1, 691 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 692 .build()); 693 KeyPair keyPair = generator.generateKeyPair(); 694 assertGeneratedKeyPairAndSelfSignedCertificate( 695 keyPair, 696 TEST_ALIAS_1, 697 "EC", 698 256, 699 DEFAULT_CERT_SUBJECT, 700 DEFAULT_CERT_SERIAL_NUMBER, 701 DEFAULT_CERT_NOT_BEFORE, 702 DEFAULT_CERT_NOT_AFTER); 703 TestUtils.assertECParameterSpecEqualsIgnoreSeedIfNotPresent( 704 ECCurves.NIST_P_256_SPEC, ((ECKey) keyPair.getPrivate()).getParams()); 705 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 706 assertEquals(256, keyInfo.getKeySize()); 707 assertEquals(TEST_ALIAS_1, keyInfo.getKeystoreAlias()); 708 assertOneOf(keyInfo.getOrigin(), 709 KeyProperties.ORIGIN_GENERATED, KeyProperties.ORIGIN_UNKNOWN); 710 assertEquals( 711 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY, keyInfo.getPurposes()); 712 assertFalse(keyInfo.isUserAuthenticationRequired()); 713 assertEquals(null, keyInfo.getKeyValidityStart()); 714 assertEquals(null, keyInfo.getKeyValidityForOriginationEnd()); 715 assertEquals(null, keyInfo.getKeyValidityForConsumptionEnd()); 716 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 717 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getDigests())); 718 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getSignaturePaddings())); 719 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getEncryptionPaddings())); 720 } 721 testGenerate_RSA_ModernSpec_Defaults()722 public void testGenerate_RSA_ModernSpec_Defaults() throws Exception { 723 KeyPairGenerator generator = getRsaGenerator(); 724 generator.initialize(new KeyGenParameterSpec.Builder( 725 TEST_ALIAS_1, 726 KeyProperties.PURPOSE_ENCRYPT | KeyProperties.PURPOSE_DECRYPT) 727 .build()); 728 KeyPair keyPair = generator.generateKeyPair(); 729 assertGeneratedKeyPairAndSelfSignedCertificate( 730 keyPair, 731 TEST_ALIAS_1, 732 "RSA", 733 2048, 734 DEFAULT_CERT_SUBJECT, 735 DEFAULT_CERT_SERIAL_NUMBER, 736 DEFAULT_CERT_NOT_BEFORE, 737 DEFAULT_CERT_NOT_AFTER); 738 assertEquals(RSAKeyGenParameterSpec.F4, 739 ((RSAPublicKey) keyPair.getPublic()).getPublicExponent()); 740 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 741 assertEquals(2048, keyInfo.getKeySize()); 742 assertEquals(TEST_ALIAS_1, keyInfo.getKeystoreAlias()); 743 assertOneOf(keyInfo.getOrigin(), 744 KeyProperties.ORIGIN_GENERATED, KeyProperties.ORIGIN_UNKNOWN); 745 assertEquals( 746 KeyProperties.PURPOSE_ENCRYPT | KeyProperties.PURPOSE_DECRYPT, 747 keyInfo.getPurposes()); 748 assertFalse(keyInfo.isUserAuthenticationRequired()); 749 assertEquals(null, keyInfo.getKeyValidityStart()); 750 assertEquals(null, keyInfo.getKeyValidityForOriginationEnd()); 751 assertEquals(null, keyInfo.getKeyValidityForConsumptionEnd()); 752 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 753 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getDigests())); 754 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getSignaturePaddings())); 755 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getEncryptionPaddings())); 756 } 757 testGenerate_EC_ModernSpec_AsCustomAsPossible()758 public void testGenerate_EC_ModernSpec_AsCustomAsPossible() throws Exception { 759 KeyPairGenerator generator = getEcGenerator(); 760 Date keyValidityStart = new Date(System.currentTimeMillis()); 761 Date keyValidityEndDateForOrigination = new Date(System.currentTimeMillis() + 1000000); 762 Date keyValidityEndDateForConsumption = new Date(System.currentTimeMillis() + 10000000); 763 764 Date certNotBefore = new Date(System.currentTimeMillis() - 1000 * 60 * 60 * 24 * 7); 765 Date certNotAfter = new Date(System.currentTimeMillis() + 1000 * 60 * 60 * 24 * 7); 766 BigInteger certSerialNumber = new BigInteger("12345678"); 767 X500Principal certSubject = new X500Principal("cn=hello"); 768 generator.initialize(new KeyGenParameterSpec.Builder( 769 TEST_ALIAS_1, 770 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY 771 | KeyProperties.PURPOSE_ENCRYPT) 772 .setKeySize(224) 773 .setDigests(KeyProperties.DIGEST_SHA384, KeyProperties.DIGEST_SHA512) 774 .setKeyValidityStart(keyValidityStart) 775 .setKeyValidityForOriginationEnd(keyValidityEndDateForOrigination) 776 .setKeyValidityForConsumptionEnd(keyValidityEndDateForConsumption) 777 .setCertificateSerialNumber(certSerialNumber) 778 .setCertificateSubject(certSubject) 779 .setCertificateNotBefore(certNotBefore) 780 .setCertificateNotAfter(certNotAfter) 781 .build()); 782 KeyPair keyPair = generator.generateKeyPair(); 783 assertGeneratedKeyPairAndSelfSignedCertificate( 784 keyPair, 785 TEST_ALIAS_1, 786 "EC", 787 224, 788 certSubject, 789 certSerialNumber, 790 certNotBefore, 791 certNotAfter); 792 TestUtils.assertECParameterSpecEqualsIgnoreSeedIfNotPresent( 793 ECCurves.NIST_P_224_SPEC, ((ECKey) keyPair.getPrivate()).getParams()); 794 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 795 assertEquals(224, keyInfo.getKeySize()); 796 assertEquals(TEST_ALIAS_1, keyInfo.getKeystoreAlias()); 797 assertOneOf(keyInfo.getOrigin(), 798 KeyProperties.ORIGIN_GENERATED, KeyProperties.ORIGIN_UNKNOWN); 799 assertEquals( 800 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY 801 | KeyProperties.PURPOSE_ENCRYPT, 802 keyInfo.getPurposes()); 803 assertEquals(keyValidityStart, keyInfo.getKeyValidityStart()); 804 assertEquals(keyValidityEndDateForOrigination, keyInfo.getKeyValidityForOriginationEnd()); 805 assertEquals(keyValidityEndDateForConsumption, keyInfo.getKeyValidityForConsumptionEnd()); 806 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 807 808 List<String> actualDigests = new ArrayList<String>(Arrays.asList(keyInfo.getDigests())); 809 // Keystore may have added DIGEST_NONE, to allow software digesting. 810 actualDigests.remove(KeyProperties.DIGEST_NONE); 811 TestUtils.assertContentsInAnyOrder( 812 actualDigests, KeyProperties.DIGEST_SHA384, KeyProperties.DIGEST_SHA512); 813 814 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getSignaturePaddings())); 815 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getEncryptionPaddings())); 816 assertFalse(keyInfo.isUserAuthenticationRequired()); 817 assertEquals(-1, keyInfo.getUserAuthenticationValidityDurationSeconds()); 818 } 819 testGenerate_RSA_ModernSpec_AsCustomAsPossible()820 public void testGenerate_RSA_ModernSpec_AsCustomAsPossible() throws Exception { 821 KeyPairGenerator generator = getRsaGenerator(); 822 Date keyValidityStart = new Date(System.currentTimeMillis()); 823 Date keyValidityEndDateForOrigination = new Date(System.currentTimeMillis() + 1000000); 824 Date keyValidityEndDateForConsumption = new Date(System.currentTimeMillis() + 10000000); 825 826 Date certNotBefore = new Date(System.currentTimeMillis() - 1000 * 60 * 60 * 24 * 210); 827 Date certNotAfter = new Date(System.currentTimeMillis() + 1000 * 60 * 60 * 24 * 210); 828 BigInteger certSerialNumber = new BigInteger("1234567890"); 829 X500Principal certSubject = new X500Principal("cn=hello2"); 830 generator.initialize(new KeyGenParameterSpec.Builder( 831 TEST_ALIAS_1, 832 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY 833 | KeyProperties.PURPOSE_ENCRYPT) 834 .setAlgorithmParameterSpec( 835 new RSAKeyGenParameterSpec(3072, RSAKeyGenParameterSpec.F0)) 836 .setKeySize(3072) 837 .setDigests(KeyProperties.DIGEST_SHA384, KeyProperties.DIGEST_SHA512) 838 .setSignaturePaddings(KeyProperties.SIGNATURE_PADDING_RSA_PSS, 839 KeyProperties.SIGNATURE_PADDING_RSA_PKCS1) 840 .setBlockModes(KeyProperties.BLOCK_MODE_ECB) 841 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_RSA_OAEP, 842 KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1) 843 .setKeyValidityStart(keyValidityStart) 844 .setKeyValidityForOriginationEnd(keyValidityEndDateForOrigination) 845 .setKeyValidityForConsumptionEnd(keyValidityEndDateForConsumption) 846 .setCertificateSerialNumber(certSerialNumber) 847 .setCertificateSubject(certSubject) 848 .setCertificateNotBefore(certNotBefore) 849 .setCertificateNotAfter(certNotAfter) 850 .build()); 851 KeyPair keyPair = generator.generateKeyPair(); 852 assertGeneratedKeyPairAndSelfSignedCertificate( 853 keyPair, 854 TEST_ALIAS_1, 855 "RSA", 856 3072, 857 certSubject, 858 certSerialNumber, 859 certNotBefore, 860 certNotAfter); 861 assertEquals(RSAKeyGenParameterSpec.F0, 862 ((RSAPublicKey) keyPair.getPublic()).getPublicExponent()); 863 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 864 assertEquals(3072, keyInfo.getKeySize()); 865 assertEquals(TEST_ALIAS_1, keyInfo.getKeystoreAlias()); 866 assertOneOf(keyInfo.getOrigin(), 867 KeyProperties.ORIGIN_GENERATED, KeyProperties.ORIGIN_UNKNOWN); 868 assertEquals( 869 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY 870 | KeyProperties.PURPOSE_ENCRYPT, 871 keyInfo.getPurposes()); 872 assertEquals(keyValidityStart, keyInfo.getKeyValidityStart()); 873 assertEquals(keyValidityEndDateForOrigination, keyInfo.getKeyValidityForOriginationEnd()); 874 assertEquals(keyValidityEndDateForConsumption, keyInfo.getKeyValidityForConsumptionEnd()); 875 876 List<String> actualDigests = 877 new ArrayList<String>(Arrays.asList(keyInfo.getDigests())); 878 // Keystore may have added DIGEST_NONE, to allow software digesting. 879 actualDigests.remove(KeyProperties.DIGEST_NONE); 880 TestUtils.assertContentsInAnyOrder( 881 actualDigests, KeyProperties.DIGEST_SHA384, KeyProperties.DIGEST_SHA512); 882 883 TestUtils.assertContentsInAnyOrder(Arrays.asList(keyInfo.getSignaturePaddings()), 884 KeyProperties.SIGNATURE_PADDING_RSA_PKCS1, 885 KeyProperties.SIGNATURE_PADDING_RSA_PSS); 886 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getBlockModes()), 887 KeyProperties.BLOCK_MODE_ECB); 888 889 List<String> actualEncryptionPaddings = 890 new ArrayList<String>(Arrays.asList(keyInfo.getEncryptionPaddings())); 891 // Keystore may have added ENCRYPTION_PADDING_NONE, to allow software padding. 892 actualEncryptionPaddings.remove(KeyProperties.ENCRYPTION_PADDING_NONE); 893 TestUtils.assertContentsInAnyOrder(actualEncryptionPaddings, 894 KeyProperties.ENCRYPTION_PADDING_RSA_OAEP, 895 KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1); 896 897 assertFalse(keyInfo.isUserAuthenticationRequired()); 898 assertEquals(-1, keyInfo.getUserAuthenticationValidityDurationSeconds()); 899 } 900 testGenerate_EC_ModernSpec_UsableForTLSPeerAuth()901 public void testGenerate_EC_ModernSpec_UsableForTLSPeerAuth() throws Exception { 902 KeyPairGenerator generator = getEcGenerator(); 903 generator.initialize(new KeyGenParameterSpec.Builder( 904 TEST_ALIAS_1, 905 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 906 .setDigests(KeyProperties.DIGEST_NONE, KeyProperties.DIGEST_SHA384) 907 .build()); 908 KeyPair keyPair = generator.generateKeyPair(); 909 assertGeneratedKeyPairAndSelfSignedCertificate( 910 keyPair, 911 TEST_ALIAS_1, 912 "EC", 913 256, 914 DEFAULT_CERT_SUBJECT, 915 DEFAULT_CERT_SERIAL_NUMBER, 916 DEFAULT_CERT_NOT_BEFORE, 917 DEFAULT_CERT_NOT_AFTER); 918 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 919 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 920 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getDigests()), 921 KeyProperties.DIGEST_NONE, KeyProperties.DIGEST_SHA384); 922 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getSignaturePaddings())); 923 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getEncryptionPaddings())); 924 assertSelfSignedCertificateSignatureVerifies(TEST_ALIAS_1); 925 assertKeyPairAndCertificateUsableForTLSPeerAuthentication(TEST_ALIAS_1); 926 } 927 testGenerate_RSA_ModernSpec_UsableForTLSPeerAuth()928 public void testGenerate_RSA_ModernSpec_UsableForTLSPeerAuth() throws Exception { 929 KeyPairGenerator generator = getRsaGenerator(); 930 generator.initialize(new KeyGenParameterSpec.Builder( 931 TEST_ALIAS_1, 932 KeyProperties.PURPOSE_SIGN 933 | KeyProperties.PURPOSE_VERIFY 934 | KeyProperties.PURPOSE_DECRYPT) 935 .setDigests(KeyProperties.DIGEST_NONE, 936 KeyProperties.DIGEST_SHA256, 937 KeyProperties.DIGEST_SHA512) 938 .setEncryptionPaddings( 939 KeyProperties.ENCRYPTION_PADDING_NONE, 940 KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1) 941 .setSignaturePaddings(KeyProperties.SIGNATURE_PADDING_RSA_PKCS1) 942 .build()); 943 KeyPair keyPair = generator.generateKeyPair(); 944 assertGeneratedKeyPairAndSelfSignedCertificate( 945 keyPair, 946 TEST_ALIAS_1, 947 "RSA", 948 2048, 949 DEFAULT_CERT_SUBJECT, 950 DEFAULT_CERT_SERIAL_NUMBER, 951 DEFAULT_CERT_NOT_BEFORE, 952 DEFAULT_CERT_NOT_AFTER); 953 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 954 MoreAsserts.assertEmpty(Arrays.asList(keyInfo.getBlockModes())); 955 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getDigests()), 956 KeyProperties.DIGEST_NONE, 957 KeyProperties.DIGEST_SHA256, 958 KeyProperties.DIGEST_SHA512); 959 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getSignaturePaddings()), 960 KeyProperties.SIGNATURE_PADDING_RSA_PKCS1); 961 MoreAsserts.assertContentsInAnyOrder(Arrays.asList(keyInfo.getEncryptionPaddings()), 962 KeyProperties.ENCRYPTION_PADDING_NONE, 963 KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1); 964 assertSelfSignedCertificateSignatureVerifies(TEST_ALIAS_1); 965 assertKeyPairAndCertificateUsableForTLSPeerAuthentication(TEST_ALIAS_1); 966 } 967 968 // TODO: Test fingerprint-authorized and secure lock screen-authorized keys. These can't 969 // currently be tested here because CTS does not require that secure lock screen is set up and 970 // that at least one fingerprint is enrolled. 971 testGenerate_EC_ModernSpec_KeyNotYetValid()972 public void testGenerate_EC_ModernSpec_KeyNotYetValid() throws Exception { 973 KeyPairGenerator generator = getEcGenerator(); 974 Date validityStart = new Date(System.currentTimeMillis() + DAY_IN_MILLIS); 975 generator.initialize(new KeyGenParameterSpec.Builder( 976 TEST_ALIAS_1, 977 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 978 .setKeySize(256) 979 .setDigests(KeyProperties.DIGEST_SHA256) 980 .setKeyValidityStart(validityStart) 981 .build()); 982 KeyPair keyPair = generator.generateKeyPair(); 983 assertGeneratedKeyPairAndSelfSignedCertificate( 984 keyPair, 985 TEST_ALIAS_1, 986 "EC", 987 256, 988 DEFAULT_CERT_SUBJECT, 989 DEFAULT_CERT_SERIAL_NUMBER, 990 DEFAULT_CERT_NOT_BEFORE, 991 DEFAULT_CERT_NOT_AFTER); 992 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 993 assertEquals(validityStart, keyInfo.getKeyValidityStart()); 994 } 995 testGenerate_RSA_ModernSpec_KeyExpiredForOrigination()996 public void testGenerate_RSA_ModernSpec_KeyExpiredForOrigination() throws Exception { 997 KeyPairGenerator generator = getRsaGenerator(); 998 Date originationEnd = new Date(System.currentTimeMillis() - DAY_IN_MILLIS); 999 generator.initialize(new KeyGenParameterSpec.Builder( 1000 TEST_ALIAS_1, 1001 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 1002 .setKeySize(1024) 1003 .setDigests(KeyProperties.DIGEST_SHA256) 1004 .setSignaturePaddings(KeyProperties.SIGNATURE_PADDING_RSA_PKCS1) 1005 .setKeyValidityForOriginationEnd(originationEnd) 1006 .build()); 1007 KeyPair keyPair = generator.generateKeyPair(); 1008 assertGeneratedKeyPairAndSelfSignedCertificate( 1009 keyPair, 1010 TEST_ALIAS_1, 1011 "RSA", 1012 1024, 1013 DEFAULT_CERT_SUBJECT, 1014 DEFAULT_CERT_SERIAL_NUMBER, 1015 DEFAULT_CERT_NOT_BEFORE, 1016 DEFAULT_CERT_NOT_AFTER); 1017 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 1018 assertEquals(originationEnd, keyInfo.getKeyValidityForOriginationEnd()); 1019 } 1020 testGenerate_EC_ModernSpec_SupportedSizes()1021 public void testGenerate_EC_ModernSpec_SupportedSizes() throws Exception { 1022 assertKeyGenUsingECSizeOnlyUsesCorrectCurve(224, ECCurves.NIST_P_224_SPEC); 1023 assertKeyGenUsingECSizeOnlyUsesCorrectCurve(256, ECCurves.NIST_P_256_SPEC); 1024 assertKeyGenUsingECSizeOnlyUsesCorrectCurve(384, ECCurves.NIST_P_384_SPEC); 1025 assertKeyGenUsingECSizeOnlyUsesCorrectCurve(521, ECCurves.NIST_P_521_SPEC); 1026 } 1027 testGenerate_EC_ModernSpec_UnsupportedSizesRejected()1028 public void testGenerate_EC_ModernSpec_UnsupportedSizesRejected() throws Exception { 1029 for (int keySizeBits = 0; keySizeBits <= 1024; keySizeBits++) { 1030 if ((keySizeBits == 224) || (keySizeBits == 256) || (keySizeBits == 384) 1031 || (keySizeBits == 521)) { 1032 // Skip supported sizes 1033 continue; 1034 } 1035 KeyPairGenerator generator = getEcGenerator(); 1036 1037 try { 1038 generator.initialize(new KeyGenParameterSpec.Builder( 1039 TEST_ALIAS_1, 1040 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 1041 .setKeySize(keySizeBits) 1042 .build()); 1043 fail("EC KeyPairGenerator initialized with unsupported key size: " 1044 + keySizeBits + " bits"); 1045 } catch (InvalidAlgorithmParameterException expected) { 1046 } 1047 } 1048 } 1049 testGenerate_EC_ModernSpec_SupportedNamedCurves()1050 public void testGenerate_EC_ModernSpec_SupportedNamedCurves() throws Exception { 1051 assertKeyGenUsingECNamedCurveSupported("P-224", ECCurves.NIST_P_224_SPEC); 1052 assertKeyGenUsingECNamedCurveSupported("p-224", ECCurves.NIST_P_224_SPEC); 1053 assertKeyGenUsingECNamedCurveSupported("secp224r1", ECCurves.NIST_P_224_SPEC); 1054 assertKeyGenUsingECNamedCurveSupported("SECP224R1", ECCurves.NIST_P_224_SPEC); 1055 1056 assertKeyGenUsingECNamedCurveSupported("P-256", ECCurves.NIST_P_256_SPEC); 1057 assertKeyGenUsingECNamedCurveSupported("p-256", ECCurves.NIST_P_256_SPEC); 1058 assertKeyGenUsingECNamedCurveSupported("secp256r1", ECCurves.NIST_P_256_SPEC); 1059 assertKeyGenUsingECNamedCurveSupported("SECP256R1", ECCurves.NIST_P_256_SPEC); 1060 assertKeyGenUsingECNamedCurveSupported("prime256v1", ECCurves.NIST_P_256_SPEC); 1061 assertKeyGenUsingECNamedCurveSupported("PRIME256V1", ECCurves.NIST_P_256_SPEC); 1062 1063 assertKeyGenUsingECNamedCurveSupported("P-384", ECCurves.NIST_P_384_SPEC); 1064 assertKeyGenUsingECNamedCurveSupported("p-384", ECCurves.NIST_P_384_SPEC); 1065 assertKeyGenUsingECNamedCurveSupported("secp384r1", ECCurves.NIST_P_384_SPEC); 1066 assertKeyGenUsingECNamedCurveSupported("SECP384R1", ECCurves.NIST_P_384_SPEC); 1067 1068 assertKeyGenUsingECNamedCurveSupported("P-521", ECCurves.NIST_P_521_SPEC); 1069 assertKeyGenUsingECNamedCurveSupported("p-521", ECCurves.NIST_P_521_SPEC); 1070 assertKeyGenUsingECNamedCurveSupported("secp521r1", ECCurves.NIST_P_521_SPEC); 1071 assertKeyGenUsingECNamedCurveSupported("SECP521R1", ECCurves.NIST_P_521_SPEC); 1072 } 1073 testGenerate_RSA_ModernSpec_SupportedSizes()1074 public void testGenerate_RSA_ModernSpec_SupportedSizes() throws Exception { 1075 assertKeyGenUsingRSASizeOnlySupported(512); 1076 assertKeyGenUsingRSASizeOnlySupported(768); 1077 assertKeyGenUsingRSASizeOnlySupported(1024); 1078 assertKeyGenUsingRSASizeOnlySupported(2048); 1079 assertKeyGenUsingRSASizeOnlySupported(3072); 1080 assertKeyGenUsingRSASizeOnlySupported(4096); 1081 1082 // The above use F4. Check that F0 is supported as well, just in case somebody is crazy 1083 // enough. 1084 assertKeyGenUsingRSAKeyGenParameterSpecSupported(new RSAKeyGenParameterSpec( 1085 2048, RSAKeyGenParameterSpec.F0)); 1086 } 1087 testGenerate_RSA_IndCpaEnforced()1088 public void testGenerate_RSA_IndCpaEnforced() throws Exception { 1089 KeyGenParameterSpec.Builder goodBuilder = new KeyGenParameterSpec.Builder( 1090 TEST_ALIAS_1, KeyProperties.PURPOSE_ENCRYPT) 1091 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_RSA_OAEP, 1092 KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1); 1093 assertKeyGenInitSucceeds("RSA", goodBuilder.build()); 1094 1095 // Should be fine because IND-CPA restriction applies only to encryption keys 1096 assertKeyGenInitSucceeds("RSA", 1097 TestUtils.buildUpon(goodBuilder, KeyProperties.PURPOSE_DECRYPT) 1098 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_NONE) 1099 .build()); 1100 1101 assertKeyGenInitThrowsInvalidAlgorithmParameterException("RSA", 1102 TestUtils.buildUpon(goodBuilder) 1103 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_NONE) 1104 .build()); 1105 1106 assertKeyGenInitSucceeds("RSA", 1107 TestUtils.buildUpon(goodBuilder) 1108 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_NONE) 1109 .setRandomizedEncryptionRequired(false) 1110 .build()); 1111 1112 // Should fail because PKCS#7 padding doesn't work with RSA 1113 assertKeyGenInitThrowsInvalidAlgorithmParameterException("RSA", 1114 TestUtils.buildUpon(goodBuilder) 1115 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_PKCS7) 1116 .build()); 1117 } 1118 testGenerate_EC_IndCpaEnforced()1119 public void testGenerate_EC_IndCpaEnforced() throws Exception { 1120 KeyGenParameterSpec.Builder goodBuilder = new KeyGenParameterSpec.Builder( 1121 TEST_ALIAS_2, KeyProperties.PURPOSE_ENCRYPT); 1122 assertKeyGenInitSucceeds("EC", goodBuilder.build()); 1123 1124 // Should be fine because IND-CPA restriction applies only to encryption keys 1125 assertKeyGenInitSucceeds("EC", 1126 TestUtils.buildUpon(goodBuilder, KeyProperties.PURPOSE_DECRYPT) 1127 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_NONE) 1128 .build()); 1129 1130 assertKeyGenInitThrowsInvalidAlgorithmParameterException("EC", 1131 TestUtils.buildUpon(goodBuilder) 1132 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_NONE) 1133 .build()); 1134 1135 assertKeyGenInitSucceeds("EC", 1136 TestUtils.buildUpon(goodBuilder) 1137 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_NONE) 1138 .setRandomizedEncryptionRequired(false) 1139 .build()); 1140 } 1141 1142 // http://b/28384942 testGenerateWithFarsiLocale()1143 public void testGenerateWithFarsiLocale() throws Exception { 1144 Locale defaultLocale = Locale.getDefault(); 1145 // Note that we use farsi here because its number formatter doesn't use 1146 // arabic digits. 1147 Locale fa_IR = Locale.forLanguageTag("fa-IR"); 1148 DecimalFormatSymbols dfs = DecimalFormatSymbols.getInstance(fa_IR); 1149 assertFalse('0' == dfs.getZeroDigit()); 1150 1151 Locale.setDefault(fa_IR); 1152 try { 1153 KeyPairGenerator keyGenerator = KeyPairGenerator.getInstance( 1154 KeyProperties.KEY_ALGORITHM_RSA, "AndroidKeyStore"); 1155 1156 keyGenerator.initialize(new KeyGenParameterSpec.Builder( 1157 TEST_ALIAS_1, KeyProperties.PURPOSE_ENCRYPT | KeyProperties.PURPOSE_DECRYPT) 1158 .setBlockModes(KeyProperties.BLOCK_MODE_ECB) 1159 .setEncryptionPaddings(KeyProperties.ENCRYPTION_PADDING_RSA_PKCS1) 1160 .build()); 1161 1162 keyGenerator.generateKeyPair(); 1163 } finally { 1164 Locale.setDefault(defaultLocale); 1165 } 1166 } 1167 assertKeyGenInitSucceeds(String algorithm, AlgorithmParameterSpec params)1168 private void assertKeyGenInitSucceeds(String algorithm, AlgorithmParameterSpec params) 1169 throws Exception { 1170 KeyPairGenerator generator = getGenerator(algorithm); 1171 generator.initialize(params); 1172 } 1173 assertKeyGenInitThrowsInvalidAlgorithmParameterException( String algorithm, AlgorithmParameterSpec params)1174 private void assertKeyGenInitThrowsInvalidAlgorithmParameterException( 1175 String algorithm, AlgorithmParameterSpec params) throws Exception { 1176 KeyPairGenerator generator = getGenerator(algorithm); 1177 try { 1178 generator.initialize(params); 1179 fail(); 1180 } catch (InvalidAlgorithmParameterException expected) {} 1181 } 1182 assertKeyGenUsingECSizeOnlyUsesCorrectCurve( int keySizeBits, ECParameterSpec expectedParams)1183 private void assertKeyGenUsingECSizeOnlyUsesCorrectCurve( 1184 int keySizeBits, ECParameterSpec expectedParams) throws Exception { 1185 KeyPairGenerator generator = getEcGenerator(); 1186 generator.initialize(new KeyGenParameterSpec.Builder( 1187 TEST_ALIAS_1, 1188 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 1189 .setKeySize(keySizeBits) 1190 .build(), 1191 mRng); 1192 mRng.resetCounters(); 1193 KeyPair keyPair = generator.generateKeyPair(); 1194 long consumedEntropyAmountBytes = mRng.getOutputSizeBytes(); 1195 int expectedKeySize = expectedParams.getCurve().getField().getFieldSize(); 1196 assertGeneratedKeyPairAndSelfSignedCertificate( 1197 keyPair, 1198 TEST_ALIAS_1, 1199 "EC", 1200 expectedKeySize, 1201 DEFAULT_CERT_SUBJECT, 1202 DEFAULT_CERT_SERIAL_NUMBER, 1203 DEFAULT_CERT_NOT_BEFORE, 1204 DEFAULT_CERT_NOT_AFTER); 1205 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 1206 assertEquals(expectedKeySize, keyInfo.getKeySize()); 1207 TestUtils.assertECParameterSpecEqualsIgnoreSeedIfNotPresent( 1208 expectedParams, 1209 ((ECKey) keyPair.getPublic()).getParams()); 1210 assertEquals(((keySizeBits + 7) / 8) * 8, consumedEntropyAmountBytes * 8); 1211 } 1212 assertKeyGenUsingECNamedCurveSupported( String curveName, ECParameterSpec expectedParams)1213 private void assertKeyGenUsingECNamedCurveSupported( 1214 String curveName, ECParameterSpec expectedParams) throws Exception { 1215 KeyPairGenerator generator = getEcGenerator(); 1216 generator.initialize(new KeyGenParameterSpec.Builder( 1217 TEST_ALIAS_1, 1218 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 1219 .setAlgorithmParameterSpec(new ECGenParameterSpec(curveName)) 1220 .build(), 1221 mRng); 1222 mRng.resetCounters(); 1223 KeyPair keyPair = generator.generateKeyPair(); 1224 long consumedEntropyAmountBytes = mRng.getOutputSizeBytes(); 1225 int expectedKeySize = expectedParams.getCurve().getField().getFieldSize(); 1226 assertGeneratedKeyPairAndSelfSignedCertificate( 1227 keyPair, 1228 TEST_ALIAS_1, 1229 "EC", 1230 expectedKeySize, 1231 DEFAULT_CERT_SUBJECT, 1232 DEFAULT_CERT_SERIAL_NUMBER, 1233 DEFAULT_CERT_NOT_BEFORE, 1234 DEFAULT_CERT_NOT_AFTER); 1235 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 1236 assertEquals(expectedKeySize, keyInfo.getKeySize()); 1237 TestUtils.assertECParameterSpecEqualsIgnoreSeedIfNotPresent( 1238 expectedParams, 1239 ((ECKey) keyPair.getPublic()).getParams()); 1240 assertEquals(((expectedKeySize + 7) / 8) * 8, consumedEntropyAmountBytes * 8); 1241 } 1242 assertKeyGenUsingRSASizeOnlySupported(int keySizeBits)1243 private void assertKeyGenUsingRSASizeOnlySupported(int keySizeBits) throws Exception { 1244 KeyPairGenerator generator = getRsaGenerator(); 1245 generator.initialize(new KeyGenParameterSpec.Builder( 1246 TEST_ALIAS_1, 1247 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 1248 .setKeySize(keySizeBits) 1249 .build(), 1250 mRng); 1251 mRng.resetCounters(); 1252 KeyPair keyPair = generator.generateKeyPair(); 1253 long consumedEntropyAmountBytes = mRng.getOutputSizeBytes(); 1254 assertGeneratedKeyPairAndSelfSignedCertificate( 1255 keyPair, 1256 TEST_ALIAS_1, 1257 "RSA", 1258 keySizeBits, 1259 DEFAULT_CERT_SUBJECT, 1260 DEFAULT_CERT_SERIAL_NUMBER, 1261 DEFAULT_CERT_NOT_BEFORE, 1262 DEFAULT_CERT_NOT_AFTER); 1263 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 1264 assertEquals(keySizeBits, keyInfo.getKeySize()); 1265 assertEquals(((keySizeBits + 7) / 8) * 8, consumedEntropyAmountBytes * 8); 1266 } 1267 assertKeyGenUsingRSAKeyGenParameterSpecSupported( RSAKeyGenParameterSpec spec)1268 private void assertKeyGenUsingRSAKeyGenParameterSpecSupported( 1269 RSAKeyGenParameterSpec spec) throws Exception { 1270 KeyPairGenerator generator = getRsaGenerator(); 1271 generator.initialize(new KeyGenParameterSpec.Builder( 1272 TEST_ALIAS_1, 1273 KeyProperties.PURPOSE_SIGN | KeyProperties.PURPOSE_VERIFY) 1274 .setAlgorithmParameterSpec(spec) 1275 .build(), 1276 mRng); 1277 mRng.resetCounters(); 1278 KeyPair keyPair = generator.generateKeyPair(); 1279 long consumedEntropyAmountBytes = mRng.getOutputSizeBytes(); 1280 assertGeneratedKeyPairAndSelfSignedCertificate( 1281 keyPair, 1282 TEST_ALIAS_1, 1283 "RSA", 1284 spec.getKeysize(), 1285 DEFAULT_CERT_SUBJECT, 1286 DEFAULT_CERT_SERIAL_NUMBER, 1287 DEFAULT_CERT_NOT_BEFORE, 1288 DEFAULT_CERT_NOT_AFTER); 1289 assertEquals(spec.getPublicExponent(), 1290 ((RSAPublicKey) keyPair.getPublic()).getPublicExponent()); 1291 KeyInfo keyInfo = TestUtils.getKeyInfo(keyPair.getPrivate()); 1292 assertEquals(spec.getKeysize(), keyInfo.getKeySize()); 1293 assertEquals(((spec.getKeysize() + 7) / 8) * 8, consumedEntropyAmountBytes * 8); 1294 } 1295 assertSelfSignedCertificateSignatureVerifies(Certificate certificate)1296 private static void assertSelfSignedCertificateSignatureVerifies(Certificate certificate) { 1297 try { 1298 certificate.verify(certificate.getPublicKey()); 1299 } catch (Exception e) { 1300 throw new RuntimeException("Failed to verify self-signed certificate signature", e); 1301 } 1302 } 1303 assertGeneratedKeyPairAndSelfSignedCertificate( KeyPair keyPair, String alias, String expectedKeyAlgorithm, int expectedKeySize, X500Principal expectedCertSubject, BigInteger expectedCertSerialNumber, Date expectedCertNotBefore, Date expectedCertNotAfter)1304 private void assertGeneratedKeyPairAndSelfSignedCertificate( 1305 KeyPair keyPair, String alias, 1306 String expectedKeyAlgorithm, 1307 int expectedKeySize, 1308 X500Principal expectedCertSubject, 1309 BigInteger expectedCertSerialNumber, 1310 Date expectedCertNotBefore, 1311 Date expectedCertNotAfter) 1312 throws Exception { 1313 assertNotNull(keyPair); 1314 TestUtils.assertKeyPairSelfConsistent(keyPair); 1315 TestUtils.assertKeySize(expectedKeySize, keyPair); 1316 assertEquals(expectedKeyAlgorithm, keyPair.getPublic().getAlgorithm()); 1317 TestUtils.assertKeyStoreKeyPair(mKeyStore, alias, keyPair); 1318 1319 X509Certificate cert = (X509Certificate) mKeyStore.getCertificate(alias); 1320 assertEquals(keyPair.getPublic(), cert.getPublicKey()); 1321 assertX509CertificateParameters(cert, 1322 expectedCertSubject, 1323 expectedCertSerialNumber, 1324 expectedCertNotBefore, 1325 expectedCertNotAfter); 1326 // Assert that the certificate chain consists only of the above certificate 1327 MoreAsserts.assertContentsInOrder( 1328 Arrays.asList(mKeyStore.getCertificateChain(alias)), cert); 1329 } 1330 assertSelfSignedCertificateSignatureVerifies(String alias)1331 private void assertSelfSignedCertificateSignatureVerifies(String alias) throws Exception { 1332 assertSelfSignedCertificateSignatureVerifies(mKeyStore.getCertificate(alias)); 1333 } 1334 assertKeyPairAndCertificateUsableForTLSPeerAuthentication(String alias)1335 private void assertKeyPairAndCertificateUsableForTLSPeerAuthentication(String alias) 1336 throws Exception { 1337 assertUsableForTLSPeerAuthentication( 1338 (PrivateKey) mKeyStore.getKey(alias, null), 1339 mKeyStore.getCertificateChain(alias)); 1340 } 1341 assertX509CertificateParameters( X509Certificate actualCert, X500Principal expectedSubject, BigInteger expectedSerialNumber, Date expectedNotBefore, Date expectedNotAfter)1342 private static void assertX509CertificateParameters( 1343 X509Certificate actualCert, 1344 X500Principal expectedSubject, BigInteger expectedSerialNumber, 1345 Date expectedNotBefore, Date expectedNotAfter) { 1346 assertEquals(expectedSubject, actualCert.getSubjectDN()); 1347 assertEquals(expectedSubject, actualCert.getIssuerDN()); 1348 assertEquals(expectedSerialNumber, actualCert.getSerialNumber()); 1349 assertDateEquals(expectedNotBefore, actualCert.getNotBefore()); 1350 assertDateEquals(expectedNotAfter, actualCert.getNotAfter()); 1351 } 1352 assertUsableForTLSPeerAuthentication( PrivateKey privateKey, Certificate[] certificateChain)1353 private static void assertUsableForTLSPeerAuthentication( 1354 PrivateKey privateKey, 1355 Certificate[] certificateChain) throws Exception { 1356 // Set up both client and server to use the same private key + cert, and to trust that cert 1357 // when it's presented by peer. This exercises the use of the private key both in client 1358 // and server scenarios. 1359 X509Certificate[] x509CertificateChain = new X509Certificate[certificateChain.length]; 1360 for (int i = 0; i < certificateChain.length; i++) { 1361 x509CertificateChain[i] = (X509Certificate) certificateChain[i]; 1362 } 1363 TestKeyStore serverKeyStore = TestKeyStore.getServer(); 1364 // Make the peer trust the root certificate in the chain. As opposed to making the peer 1365 // trust the leaf certificate, this will ensure that the whole chain verifies. 1366 serverKeyStore.keyStore.setCertificateEntry( 1367 "trusted", certificateChain[certificateChain.length - 1]); 1368 SSLContext serverContext = TestSSLContext.createSSLContext("TLS", 1369 new KeyManager[] { 1370 TestKeyManager.wrap(new MyKeyManager(privateKey, x509CertificateChain)) 1371 }, 1372 TestKeyStore.createTrustManagers(serverKeyStore.keyStore)); 1373 SSLContext clientContext = serverContext; 1374 1375 if ("EC".equalsIgnoreCase(privateKey.getAlgorithm())) { 1376 // As opposed to RSA (see below) EC keys are used in the same way in all cipher suites. 1377 // Assert that the key works with the default list of cipher suites. 1378 assertSSLConnectionWithClientAuth( 1379 clientContext, serverContext, null, x509CertificateChain, x509CertificateChain); 1380 } else if ("RSA".equalsIgnoreCase(privateKey.getAlgorithm())) { 1381 // RSA keys are used differently between Forward Secure and non-Forward Secure cipher 1382 // suites. For example, RSA key exchange requires the server to decrypt using its RSA 1383 // private key, whereas ECDHE_RSA key exchange requires the server to sign usnig its 1384 // RSA private key. We thus assert that the key works with Forward Secure cipher suites 1385 // and that it works with non-Forward Secure cipher suites. 1386 List<String> fsCipherSuites = new ArrayList<String>(); 1387 List<String> nonFsCipherSuites = new ArrayList<String>(); 1388 for (String cipherSuite : clientContext.getDefaultSSLParameters().getCipherSuites()) { 1389 if (cipherSuite.contains("_ECDHE_RSA_") || cipherSuite.contains("_DHE_RSA_")) { 1390 fsCipherSuites.add(cipherSuite); 1391 } else if (cipherSuite.contains("_RSA_WITH_")) { 1392 nonFsCipherSuites.add(cipherSuite); 1393 } 1394 } 1395 assertFalse("No FS RSA cipher suites enabled by default", fsCipherSuites.isEmpty()); 1396 assertFalse("No non-FS RSA cipher suites enabled", nonFsCipherSuites.isEmpty()); 1397 1398 // Assert that the key works with RSA Forward Secure cipher suites. 1399 assertSSLConnectionWithClientAuth( 1400 clientContext, serverContext, fsCipherSuites.toArray(new String[0]), 1401 x509CertificateChain, x509CertificateChain); 1402 // Assert that the key works with RSA non-Forward Secure cipher suites. 1403 assertSSLConnectionWithClientAuth( 1404 clientContext, serverContext, nonFsCipherSuites.toArray(new String[0]), 1405 x509CertificateChain, x509CertificateChain); 1406 } else { 1407 fail("Unsupported key algorithm: " + privateKey.getAlgorithm()); 1408 } 1409 } 1410 assertSSLConnectionWithClientAuth( SSLContext clientContext, SSLContext serverContext, String[] enabledCipherSuites, X509Certificate[] expectedClientCertChain, X509Certificate[] expectedServerCertChain)1411 private static void assertSSLConnectionWithClientAuth( 1412 SSLContext clientContext, SSLContext serverContext, String[] enabledCipherSuites, 1413 X509Certificate[] expectedClientCertChain, X509Certificate[] expectedServerCertChain) 1414 throws Exception { 1415 SSLServerSocket serverSocket = (SSLServerSocket) serverContext.getServerSocketFactory() 1416 .createServerSocket(0); 1417 InetAddress host = InetAddress.getLocalHost(); 1418 int port = serverSocket.getLocalPort(); 1419 SSLSocket client = (SSLSocket) clientContext.getSocketFactory().createSocket(host, port); 1420 1421 final SSLSocket server = (SSLSocket) serverSocket.accept(); 1422 ExecutorService executor = Executors.newSingleThreadExecutor(); 1423 Future<Certificate[]> future = executor.submit(new Callable<Certificate[]>() { 1424 @Override 1425 public Certificate[] call() throws Exception { 1426 server.setNeedClientAuth(true); 1427 server.setWantClientAuth(true); 1428 server.startHandshake(); 1429 return server.getSession().getPeerCertificates(); 1430 } 1431 }); 1432 executor.shutdown(); 1433 if (enabledCipherSuites != null) { 1434 client.setEnabledCipherSuites(enabledCipherSuites); 1435 } 1436 client.startHandshake(); 1437 Certificate[] usedServerCerts = client.getSession().getPeerCertificates(); 1438 Certificate[] usedClientCerts = future.get(); 1439 client.close(); 1440 server.close(); 1441 1442 assertNotNull(usedServerCerts); 1443 assertEquals(Arrays.asList(expectedServerCertChain), Arrays.asList(usedServerCerts)); 1444 1445 assertNotNull(usedClientCerts); 1446 assertEquals(Arrays.asList(expectedClientCertChain), Arrays.asList(usedClientCerts)); 1447 } 1448 1449 private static class MyKeyManager extends X509ExtendedKeyManager { 1450 private final PrivateKey key; 1451 private final X509Certificate[] chain; 1452 MyKeyManager(PrivateKey key, X509Certificate[] certChain)1453 public MyKeyManager(PrivateKey key, X509Certificate[] certChain) { 1454 this.key = key; 1455 this.chain = certChain; 1456 } 1457 1458 @Override chooseClientAlias(String[] keyType, Principal[] issuers, Socket socket)1459 public String chooseClientAlias(String[] keyType, Principal[] issuers, Socket socket) { 1460 return "fake"; 1461 } 1462 1463 @Override chooseServerAlias(String keyType, Principal[] issuers, Socket socket)1464 public String chooseServerAlias(String keyType, Principal[] issuers, Socket socket) { 1465 return "fake"; 1466 } 1467 1468 @Override getCertificateChain(String alias)1469 public X509Certificate[] getCertificateChain(String alias) { 1470 return chain; 1471 } 1472 1473 @Override getClientAliases(String keyType, Principal[] issuers)1474 public String[] getClientAliases(String keyType, Principal[] issuers) { 1475 return new String[] { "fake" }; 1476 } 1477 1478 @Override getServerAliases(String keyType, Principal[] issuers)1479 public String[] getServerAliases(String keyType, Principal[] issuers) { 1480 return new String[] { "fake" }; 1481 } 1482 1483 @Override getPrivateKey(String alias)1484 public PrivateKey getPrivateKey(String alias) { 1485 return key; 1486 } 1487 } 1488 1489 assertDateEquals(Date date1, Date date2)1490 private static void assertDateEquals(Date date1, Date date2) { 1491 assertDateEquals(null, date1, date2); 1492 } 1493 assertDateEquals(String message, Date date1, Date date2)1494 private static void assertDateEquals(String message, Date date1, Date date2) { 1495 SimpleDateFormat formatter = new SimpleDateFormat("dd MMM yyyy HH:mm:ss"); 1496 1497 String result1 = formatter.format(date1); 1498 String result2 = formatter.format(date2); 1499 1500 assertEquals(message, result1, result2); 1501 } 1502 getRsaGenerator()1503 private KeyPairGenerator getRsaGenerator() 1504 throws NoSuchAlgorithmException, NoSuchProviderException { 1505 return getGenerator("RSA"); 1506 } 1507 getEcGenerator()1508 private KeyPairGenerator getEcGenerator() 1509 throws NoSuchAlgorithmException, NoSuchProviderException { 1510 return getGenerator("EC"); 1511 } 1512 getGenerator(String algorithm)1513 private KeyPairGenerator getGenerator(String algorithm) 1514 throws NoSuchAlgorithmException, NoSuchProviderException { 1515 return KeyPairGenerator.getInstance(algorithm, "AndroidKeyStore"); 1516 } 1517 assertOneOf(int actual, int... expected)1518 private static void assertOneOf(int actual, int... expected) { 1519 assertOneOf(null, actual, expected); 1520 } 1521 assertOneOf(String message, int actual, int... expected)1522 private static void assertOneOf(String message, int actual, int... expected) { 1523 for (int expectedValue : expected) { 1524 if (actual == expectedValue) { 1525 return; 1526 } 1527 } 1528 fail(((message != null) ? message + ". " : "") 1529 + "Expected one of " + Arrays.asList(expected) 1530 + ", actual: <" + actual + ">"); 1531 } 1532 getWorkingSpec()1533 private KeyGenParameterSpec.Builder getWorkingSpec() { 1534 return getWorkingSpec(0); 1535 } 1536 getWorkingSpec(int purposes)1537 private KeyGenParameterSpec.Builder getWorkingSpec(int purposes) { 1538 return new KeyGenParameterSpec.Builder(TEST_ALIAS_1, purposes); 1539 } 1540 } 1541