1 /** 2 * Licensed under the Apache License, Version 2.0 (the "License"); 3 * you may not use this file except in compliance with the License. 4 * You may obtain a copy of the License at 5 * 6 * http://www.apache.org/licenses/LICENSE-2.0 7 * 8 * Unless required by applicable law or agreed to in writing, software 9 * distributed under the License is distributed on an "AS IS" BASIS, 10 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 11 * See the License for the specific language governing permissions and 12 * limitations under the License. 13 */ 14 package com.google.security.wycheproof; 15 16 import static org.junit.Assert.assertEquals; 17 import static org.junit.Assert.assertTrue; 18 19 import com.google.gson.JsonElement; 20 import com.google.gson.JsonObject; 21 import com.google.security.wycheproof.WycheproofRunner.ExcludedTest; 22 import com.google.security.wycheproof.WycheproofRunner.NoPresubmitTest; 23 import com.google.security.wycheproof.WycheproofRunner.ProviderType; 24 import java.security.GeneralSecurityException; 25 import java.security.InvalidKeyException; 26 import java.security.KeyFactory; 27 import java.security.NoSuchAlgorithmException; 28 import java.security.PrivateKey; 29 import java.security.PublicKey; 30 import java.security.Signature; 31 import java.security.SignatureException; 32 import java.security.spec.PKCS8EncodedKeySpec; 33 import java.security.spec.X509EncodedKeySpec; 34 import java.util.HashSet; 35 import java.util.Set; 36 import org.junit.Test; 37 import org.junit.runner.RunWith; 38 import org.junit.runners.JUnit4; 39 40 /** 41 * This test uses test vectors in JSON format to check digital signature schemes. There are still a 42 * lot of open questions, e.g. the format for the test vectors is not yet finalized. Therefore, we 43 * are not integrating the tests here into other tests 44 */ 45 @RunWith(JUnit4.class) 46 public class JsonSignatureTest { 47 48 /** 49 * Defines the format of the signatures. RAW is used when the signature scheme already 50 * defines an encoding (e.g. this is used for RSA signatures). 51 */ 52 public enum Format { RAW, ASN, P1363 }; 53 54 /** Convenience method to get a String from a JsonObject */ getString(JsonObject object, String name)55 protected static String getString(JsonObject object, String name) { 56 return object.get(name).getAsString(); 57 } 58 59 /** Convenience method to get a byte array from a JsonObject */ getBytes(JsonObject object, String name)60 protected static byte[] getBytes(JsonObject object, String name) throws Exception { 61 return JsonUtil.asByteArray(object.get(name)); 62 } 63 64 /** 65 * Convert hash names, so that they can be used in an algorithm name for a signature. The 66 * algorithm names used in JCA are a bit inconsequential. E.g. a dash is necessary for message 67 * digests (e.g. "SHA-256") but are not used in the corresponding names for digital signatures 68 * (e.g. "SHA256WITHECDSA"). Providers sometimes use distinct algorithm names for the same 69 * cryptographic primitive. On the other hand, the dash remains for SHA-3. Hence, the correct 70 * name for ECDSA with SHA3-256 is "SHA3-256WithECDSA". 71 * 72 * <p>See https://docs.oracle.com/en/java/javase/11/docs/specs/security/standard-names.html 73 * 74 * @param md the name of a message digest 75 * @return the name of the message digest when used in a signature algorithm. 76 */ convertMdName(String md)77 protected static String convertMdName(String md) { 78 if (md.equalsIgnoreCase("SHA-1")) { 79 return "SHA1"; 80 } else if (md.equalsIgnoreCase("SHA-224")) { 81 return "SHA224"; 82 } else if (md.equalsIgnoreCase("SHA-256")) { 83 return "SHA256"; 84 } else if (md.equalsIgnoreCase("SHA-384")) { 85 return "SHA384"; 86 } else if (md.equalsIgnoreCase("SHA-512")) { 87 return "SHA512"; 88 } else if (md.equalsIgnoreCase("SHA-512/224")) { 89 return "SHA512/224"; 90 } else if (md.equalsIgnoreCase("SHA-512/256")) { 91 return "SHA512/256"; 92 } 93 return md; 94 } 95 96 /** 97 * Returns an instance of java.security.Signature for an algorithm name, a digest name and a 98 * signature format. 99 * 100 * @param md the name of the message digest (e.g. "SHA-256") 101 * @param signatureAlgorithm the name of the signature algorithm (e.g. "ECDSA") 102 * @param signatureFormat the format of the signatures. 103 * @return an instance of java.security.Signature if the algorithm is known 104 * @throws NoSuchAlgorithmException if the algorithm is not known 105 */ getSignatureInstance( JsonObject group, String signatureAlgorithm, Format signatureFormat)106 protected static Signature getSignatureInstance( 107 JsonObject group, String signatureAlgorithm, Format signatureFormat) 108 throws NoSuchAlgorithmException { 109 String md = ""; 110 if (group.has("sha")) { 111 md = convertMdName(getString(group, "sha")); 112 } 113 if (signatureAlgorithm.equals("ECDSA") || signatureAlgorithm.equals("DSA")) { 114 if (signatureFormat == Format.ASN) { 115 return Signature.getInstance(md + "WITH" + signatureAlgorithm); 116 } else if (signatureFormat == Format.P1363) { 117 // The algorithm names for signature schemes with P1363 format have distinct names 118 // in distinct providers. This is mainly the case since the P1363 format has only 119 // been added in jdk11, while providers such as BouncyCastle added the format earlier 120 // than that. Hence the code below just tries known algorithm names. 121 try { 122 String jdkName = md + "WITH" + signatureAlgorithm + "inP1363Format"; 123 return Signature.getInstance(jdkName); 124 } catch (NoSuchAlgorithmException ex) { 125 // jdkName is not known. 126 } 127 try { 128 String bcName = md + "WITHPLAIN-" + signatureAlgorithm; 129 return Signature.getInstance(bcName); 130 } catch (NoSuchAlgorithmException ex) { 131 // bcName is not known. 132 } 133 } 134 } else if (signatureAlgorithm.equals("RSA")) { 135 if (signatureFormat == Format.RAW) { 136 return Signature.getInstance(md + "WITH" + signatureAlgorithm); 137 } 138 } else if (signatureAlgorithm.equals("ED25519") || signatureAlgorithm.equals("ED448")) { 139 if (signatureFormat == Format.RAW) { 140 // http://openjdk.java.net/jeps/339 141 try { 142 return Signature.getInstance(signatureAlgorithm); 143 } catch (NoSuchAlgorithmException ex) { 144 // signatureAlgorithm is not known. 145 } 146 // An alternative name (e.g. used by BouncyCastle) is "EDDSA". 147 try { 148 return Signature.getInstance("EDDSA"); 149 } catch (NoSuchAlgorithmException ex) { 150 // "EDDSA" is not known either. 151 } 152 } 153 } 154 throw new NoSuchAlgorithmException( 155 "Algorithm " 156 + signatureAlgorithm 157 + " with format " 158 + signatureFormat 159 + " is not supported"); 160 } 161 162 /** 163 * Returns the expected JSON schema for a given test or "" if the schema is undefined. 164 * The purpose of this function is to perform a sanity test with the goal to recognize 165 * incorrect test setups. 166 * @param signatureAlgorithm the signataure algorithm (e.g. "ECDSA") 167 * @param signatureFormat the format of the signatures 168 * @param verify true if verification is tested, false if signature generations is tested. 169 */ expectedSchema(String signatureAlgorithm, Format signatureFormat, boolean verify)170 protected static String expectedSchema(String signatureAlgorithm, Format signatureFormat, 171 boolean verify) { 172 if (verify) { 173 if (signatureAlgorithm.equals("ECDSA")) { 174 switch (signatureFormat) { 175 case ASN: return "ecdsa_verify_schema.json"; 176 case P1363: return "ecdsa_p1363_verify_schema.json"; 177 default: break; 178 } 179 } else if (signatureAlgorithm.equals("DSA")) { 180 switch (signatureFormat) { 181 case ASN: return "dsa_verify_schema.json"; 182 case P1363: return "dsa_p1363_verify_schema.json"; 183 default: break; 184 } 185 } else if (signatureAlgorithm.equals("RSA")) { 186 // Only RSA-PKCS1 is implemented in this unit test. 187 // RSA-PSS signatures have their own unit test, because the algorithm parameters 188 // require a setup that is a little different. 189 switch (signatureFormat) { 190 case RAW: return "rsassa_pkcs1_verify_schema.json"; 191 default: break; 192 } 193 } else if (signatureAlgorithm.equals("ED25519") || signatureAlgorithm.equals("ED448")) { 194 switch (signatureFormat) { 195 case RAW: 196 return "eddsa_verify_schema.json"; 197 default: 198 break; 199 } 200 } 201 } else { 202 // signature generation 203 if (signatureAlgorithm.equals("RSA")) { 204 return "rsassa_pkcs1_generate_schema.json"; 205 } else if (signatureAlgorithm.equals("ED25519") || signatureAlgorithm.equals("ED448")) { 206 // TODO(bleichen): 207 switch (signatureFormat) { 208 case RAW: 209 return "eddsa_verify_schema.json"; 210 default: 211 break; 212 } 213 } 214 } 215 // If the schema is not defined then the tests below still run. The only drawback is that 216 // incorrect test setups are not recognized and will probably lead to failures later. 217 return ""; 218 } 219 /** 220 * Get a PublicKey from a JsonObject. 221 * 222 * <p>object contains the key in multiple formats: "key" : elements of the public key "keyDer": 223 * the key in ASN encoding encoded hexadecimal "keyPem": the key in Pem format encoded hexadecimal 224 * The test can use the format that is most convenient. 225 */ 226 // This is a false positive, since errorprone cannot track values passed into a method. 227 @SuppressWarnings("InsecureCryptoUsage") getPublicKey(JsonObject group, String algorithm)228 protected static PublicKey getPublicKey(JsonObject group, String algorithm) throws Exception { 229 KeyFactory kf; 230 if (algorithm.equals("ECDSA")) { 231 kf = KeyFactory.getInstance("EC"); 232 } else if (algorithm.equals("ED25519") || algorithm.equals("ED448")) { 233 // http://openjdk.java.net/jeps/339 234 kf = KeyFactory.getInstance("EdDSA"); 235 } else { 236 kf = KeyFactory.getInstance(algorithm); 237 } 238 byte[] encoded = TestUtil.hexToBytes(getString(group, "keyDer")); 239 X509EncodedKeySpec x509keySpec = new X509EncodedKeySpec(encoded); 240 return kf.generatePublic(x509keySpec); 241 } 242 243 /** 244 * Get a PrivateKey from a JsonObject. 245 */ 246 // This is a false positive, since errorprone cannot track values passed into a method. 247 @SuppressWarnings("InsecureCryptoUsage") getPrivateKey(JsonObject object, String algorithm)248 protected static PrivateKey getPrivateKey(JsonObject object, String algorithm) throws Exception { 249 if (algorithm.equals("RSA")) { 250 KeyFactory kf = KeyFactory.getInstance(algorithm); 251 byte[] encoded = TestUtil.hexToBytes(getString(object, "privateKeyPkcs8")); 252 PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(encoded); 253 return kf.generatePrivate(keySpec); 254 } else { 255 throw new NoSuchAlgorithmException("Algorithm " + algorithm + " is not supported"); 256 } 257 } 258 259 /** 260 * Tests the signature verification with test vectors in a given JSON file. 261 * 262 * <p> Example format for test vectors 263 * { 264 * "algorithm": "ECDSA", 265 * "generatorVersion": "0.0a13", 266 * "numberOfTests": 217, 267 * "testGroups": [ 268 * { 269 * "key": { 270 * "curve": "secp256r1", 271 * "type": "ECPublicKey", 272 * "wx": "0c9c4bc2617c81eb2dcbfda2db2a370a955be86a0d2e95fcb86a99f90cf046573", 273 * "wy": "0c400363b1b6bcc3595a7d6d3575ccebcbb03f90ba8e58da2bc4824272f4fecff" 274 * }, 275 * "keyDer": <X509encoded key> 276 * "keyPem": "-----BEGIN PUBLIC KEY-----\ ... \n-----END PUBLIC KEY-----", 277 * "sha": "SHA-256", 278 * "tests": [ 279 * { 280 * "comment": "random signature", 281 * "msg": "48656c6c6f", 282 * "result": "valid", 283 * "sig": "...", 284 * "tcId": 1 285 * }, 286 * ... 287 * } 288 * 289 * @param filename the filename of the test vectors 290 * @param signatureAlgorithm the algorithm name of the test vectors 291 * @param signatureFormat the format of the signatures. This should be Format.P1363 for 292 * P1363 encoded signatures Format.ASN for ASN.1 encoded signature and Format.RAW 293 otherwise. 294 * @param allowSkippingKeys if true then keys that cannot be constructed will not fail the test. 295 * This is for example used for files with test vectors that use elliptic curves that are not 296 * commonly supported. 297 **/ testVerification( String filename, String signatureAlgorithm, Format signatureFormat, boolean allowSkippingKeys)298 public void testVerification( 299 String filename, String signatureAlgorithm, Format signatureFormat, boolean allowSkippingKeys) 300 throws Exception { 301 JsonObject test = JsonUtil.getTestVectors(filename); 302 // Checks whether the test vectors in the file use the expected algorithm and the expected 303 // format for the signatures. 304 String schema = expectedSchema(signatureAlgorithm, signatureFormat, true); 305 String actualSchema = getString(test, "schema"); 306 if (!schema.isEmpty() && !schema.equals(actualSchema)) { 307 System.out.println( 308 signatureAlgorithm 309 + ": expecting test vectors with schema " 310 + schema 311 + " found vectors with schema " 312 + actualSchema); 313 } 314 int numTests = test.get("numberOfTests").getAsInt(); 315 int cntTests = 0; 316 int verifiedSignatures = 0; 317 int errors = 0; 318 int skippedKeys = 0; 319 int skippedAlgorithms = 0; 320 int supportedKeys = 0; 321 Set<String> skippedGroups = new HashSet<String>(); 322 for (JsonElement g : test.getAsJsonArray("testGroups")) { 323 JsonObject group = g.getAsJsonObject(); 324 PublicKey key; 325 try { 326 key = getPublicKey(group, signatureAlgorithm); 327 } catch (GeneralSecurityException ex) { 328 if (!allowSkippingKeys) { 329 throw ex; 330 } 331 if (group.has("key")) { 332 JsonObject keyStruct = group.getAsJsonObject("key"); 333 if (keyStruct.has("curve")) { 334 skippedGroups.add("curve = " + getString(keyStruct, "curve")); 335 } 336 } 337 skippedKeys++; 338 continue; 339 } 340 Signature verifier; 341 try { 342 verifier = getSignatureInstance(group, signatureAlgorithm, signatureFormat); 343 } catch (NoSuchAlgorithmException ex) { 344 if (!allowSkippingKeys) { 345 throw ex; 346 } 347 skippedAlgorithms++; 348 continue; 349 } 350 supportedKeys++; 351 for (JsonElement t : group.getAsJsonArray("tests")) { 352 cntTests++; 353 JsonObject testcase = t.getAsJsonObject(); 354 byte[] message = getBytes(testcase, "msg"); 355 byte[] signature = getBytes(testcase, "sig"); 356 int tcid = testcase.get("tcId").getAsInt(); 357 String sig = TestUtil.bytesToHex(signature); 358 String result = getString(testcase, "result"); 359 verifier.initVerify(key); 360 verifier.update(message); 361 boolean verified = false; 362 Exception failure = null; 363 try { 364 verified = verifier.verify(signature); 365 } catch (SignatureException ex) { 366 // verify can throw SignatureExceptions if the signature is malformed. 367 // We don't flag these cases and simply consider the signature as invalid. 368 verified = false; 369 failure = ex; 370 } catch (java.lang.ArithmeticException ex) { 371 // b/33446454 The Sun provider may throw an ArithmeticException instead of 372 // the expected SignatureException for DSA signatures. 373 // We should eventually remove this. 374 verified = false; 375 failure = ex; 376 } catch (Exception ex) { 377 // Other exceptions (i.e. unchecked exceptions) are considered as error 378 // since a third party should never be able to cause such exceptions. 379 System.out.println( 380 signatureAlgorithm 381 + " signature throws " 382 + ex.toString() 383 + " " 384 + filename 385 + " tcId:" 386 + tcid 387 + " sig:" 388 + sig); 389 verified = false; 390 failure = ex; 391 errors++; 392 } 393 if (!verified && result.equals("valid")) { 394 String reason = ""; 395 if (failure != null) { 396 reason = " reason:" + failure; 397 } 398 System.out.println( 399 "Valid " 400 + signatureAlgorithm 401 + " signature not verified." 402 + " " 403 + filename 404 + " tcId:" 405 + tcid 406 + " sig:" 407 + sig 408 + reason); 409 errors++; 410 } else if (verified) { 411 if (result.equals("invalid")) { 412 System.out.println( 413 "Invalid" 414 + signatureAlgorithm 415 + " signature verified." 416 + " " 417 + filename 418 + " tcId:" 419 + tcid 420 + " sig:" 421 + sig); 422 errors++; 423 } else { 424 verifiedSignatures++; 425 } 426 } 427 } 428 } 429 // Prints some information if tests were skipped. This avoids giving 430 // the impression that algorithms are supported. 431 if (skippedKeys > 0 || skippedAlgorithms > 0 || verifiedSignatures == 0) { 432 System.out.println( 433 "File:" 434 + filename 435 + " number of skipped keys:" 436 + skippedKeys 437 + " number of skipped algorithms:" 438 + skippedAlgorithms 439 + " number of supported keys:" 440 + supportedKeys 441 + " verified signatures:" 442 + verifiedSignatures); 443 for (String s : skippedGroups) { 444 System.out.println("Skipped groups where " + s); 445 } 446 } 447 assertEquals(0, errors); 448 if (skippedKeys == 0 && skippedAlgorithms == 0) { 449 assertEquals(numTests, cntTests); 450 } 451 } 452 453 /** 454 * Tests signature generation of deterministic signature schemes such as RSA-PKCS#1 v1.5. 455 * 456 * <p>The test expects that signatures are fully complying with the standards. 457 * E.g. it is acceptable when RSA-PKCS#1 verification considers ASN encodings of the 458 * digest name with a missing NULL value for legacy reasons. However, it is considered not 459 * acceptable when the signature generation does not include the NULL value. 460 * 461 * @param filename the filename of the test vectors 462 * @param signatureAlgorithm the algorithm name of the test vectors (e.g. "RSA") 463 * @param signatureFormat the format of the signatures. 464 * @param allowSkippingKeys if true then keys that cannot be constructed will not fail the test. 465 */ testSigning( String filename, String signatureAlgorithm, Format signatureFormat, boolean allowSkippingKeys)466 public void testSigning( 467 String filename, String signatureAlgorithm, Format signatureFormat, 468 boolean allowSkippingKeys) throws Exception { 469 JsonObject test = JsonUtil.getTestVectors(filename); 470 // Checks whether the test vectors in the file use the expected algorithm and the expected 471 // format for the signatures. 472 String schema = expectedSchema(signatureAlgorithm, signatureFormat, false); 473 String actualSchema = getString(test, "schema"); 474 if (!schema.isEmpty() && !schema.equals(actualSchema)) { 475 System.out.println( 476 signatureAlgorithm 477 + ": expecting test vectors with schema " 478 + schema 479 + " found vectors with schema " 480 + actualSchema); 481 } 482 int cntTests = 0; 483 int errors = 0; 484 int skippedKeys = 0; 485 for (JsonElement g : test.getAsJsonArray("testGroups")) { 486 JsonObject group = g.getAsJsonObject(); 487 PrivateKey key; 488 try { 489 key = getPrivateKey(group, signatureAlgorithm); 490 } catch (GeneralSecurityException ex) { 491 skippedKeys++; 492 continue; 493 } 494 Signature signer; 495 try { 496 signer = getSignatureInstance(group, signatureAlgorithm, signatureFormat); 497 } catch (NoSuchAlgorithmException ex) { 498 skippedKeys++; 499 continue; 500 } 501 for (JsonElement t : group.getAsJsonArray("tests")) { 502 JsonObject testcase = t.getAsJsonObject(); 503 String result = getString(testcase, "result"); 504 byte[] message = getBytes(testcase, "msg"); 505 byte[] signature = getBytes(testcase, "sig"); 506 int tcid = testcase.get("tcId").getAsInt(); 507 String expectedSig = TestUtil.bytesToHex(signature); 508 try { 509 signer.initSign(key); 510 signer.update(message); 511 String sig = TestUtil.bytesToHex(signer.sign()); 512 if (!sig.equals(expectedSig)) { 513 System.out.println( 514 "Incorrect signature generated " 515 + filename 516 + " tcId:" 517 + tcid 518 + " expected:" 519 + expectedSig 520 + " sig:" 521 + sig); 522 errors++; 523 } else { 524 cntTests++; 525 } 526 } catch (InvalidKeyException | SignatureException ex) { 527 if (result.equals("valid")) { 528 System.out.println( 529 "Failed to sign " 530 + filename 531 + " tcId:" 532 + tcid 533 + " with exception:" 534 + ex); 535 536 errors++; 537 } 538 } 539 } 540 } 541 assertEquals(0, errors); 542 if (skippedKeys > 0) { 543 System.out.println("File:" + filename); 544 System.out.println("Number of signatures verified:" + cntTests); 545 System.out.println("Number of skipped keys:" + skippedKeys); 546 assertTrue(allowSkippingKeys); 547 } 548 } 549 550 @Test testEcdsa()551 public void testEcdsa() throws Exception { 552 testVerification("ecdsa_test.json", "ECDSA", Format.ASN, true); 553 } 554 555 @Test testSecp224r1Sha224()556 public void testSecp224r1Sha224() throws Exception { 557 testVerification("ecdsa_secp224r1_sha224_test.json", "ECDSA", Format.ASN, false); 558 } 559 560 @Test testSecp224r1Sha256()561 public void testSecp224r1Sha256() throws Exception { 562 testVerification("ecdsa_secp224r1_sha256_test.json", "ECDSA", Format.ASN, false); 563 } 564 565 @Test testSecp224r1Sha512()566 public void testSecp224r1Sha512() throws Exception { 567 testVerification("ecdsa_secp224r1_sha512_test.json", "ECDSA", Format.ASN, false); 568 } 569 570 @Test testSecp256r1Sha256()571 public void testSecp256r1Sha256() throws Exception { 572 testVerification("ecdsa_secp256r1_sha256_test.json", "ECDSA", Format.ASN, false); 573 } 574 575 @Test testSecp256r1Sha512()576 public void testSecp256r1Sha512() throws Exception { 577 testVerification("ecdsa_secp256r1_sha512_test.json", "ECDSA", Format.ASN, false); 578 } 579 580 @Test testSecp384r1Sha384()581 public void testSecp384r1Sha384() throws Exception { 582 testVerification("ecdsa_secp384r1_sha384_test.json", "ECDSA", Format.ASN, false); 583 } 584 585 @Test testSecp384r1Sha512()586 public void testSecp384r1Sha512() throws Exception { 587 testVerification("ecdsa_secp384r1_sha512_test.json", "ECDSA", Format.ASN, false); 588 } 589 590 @Test testSecp521r1Sha512()591 public void testSecp521r1Sha512() throws Exception { 592 testVerification("ecdsa_secp521r1_sha512_test.json", "ECDSA", Format.ASN, false); 593 } 594 595 // Testing curves that may not be supported by a provider. 596 @Test testSecp256k1Sha256()597 public void testSecp256k1Sha256() throws Exception { 598 testVerification("ecdsa_secp256k1_sha256_test.json", "ECDSA", Format.ASN, true); 599 } 600 601 @Test testSecp256k1Sha512()602 public void testSecp256k1Sha512() throws Exception { 603 testVerification("ecdsa_secp256k1_sha512_test.json", "ECDSA", Format.ASN, true); 604 } 605 606 @NoPresubmitTest( 607 providers = {ProviderType.OPENJDK}, 608 bugs = {"b/117643131"} 609 ) 610 @Test testBrainpoolP224r1Sha224()611 public void testBrainpoolP224r1Sha224() throws Exception { 612 testVerification("ecdsa_brainpoolP224r1_sha224_test.json", "ECDSA", Format.ASN, true); 613 } 614 615 @Test testBrainpoolP256r1Sha256()616 public void testBrainpoolP256r1Sha256() throws Exception { 617 testVerification("ecdsa_brainpoolP256r1_sha256_test.json", "ECDSA", Format.ASN, true); 618 } 619 620 @Test testBrainpoolP320r1Sha384()621 public void testBrainpoolP320r1Sha384() throws Exception { 622 testVerification("ecdsa_brainpoolP320r1_sha384_test.json", "ECDSA", Format.ASN, true); 623 } 624 625 @Test testBrainpoolP384r1Sha384()626 public void testBrainpoolP384r1Sha384() throws Exception { 627 testVerification("ecdsa_brainpoolP384r1_sha384_test.json", "ECDSA", Format.ASN, true); 628 } 629 630 @Test testBrainpoolP512r1Sha512()631 public void testBrainpoolP512r1Sha512() throws Exception { 632 testVerification("ecdsa_brainpoolP512r1_sha512_test.json", "ECDSA", Format.ASN, true); 633 } 634 635 // SHA-3 signatures 636 @Test testSecp224r1Sha3_224()637 public void testSecp224r1Sha3_224 () throws Exception { 638 testVerification("ecdsa_secp224r1_sha3_224_test.json", "ECDSA", Format.ASN, true); 639 } 640 641 @Test testSecp224r1Sha3_256()642 public void testSecp224r1Sha3_256 () throws Exception { 643 testVerification("ecdsa_secp224r1_sha3_256_test.json", "ECDSA", Format.ASN, true); 644 } 645 646 @Test testSecp224r1Sha3_512()647 public void testSecp224r1Sha3_512 () throws Exception { 648 testVerification("ecdsa_secp224r1_sha3_512_test.json", "ECDSA", Format.ASN, true); 649 } 650 651 @Test testSecp256r1Sha3_256()652 public void testSecp256r1Sha3_256 () throws Exception { 653 testVerification("ecdsa_secp256r1_sha3_256_test.json", "ECDSA", Format.ASN, true); 654 } 655 656 @Test testSecp256r1Sha3_512()657 public void testSecp256r1Sha3_512 () throws Exception { 658 testVerification("ecdsa_secp256r1_sha3_512_test.json", "ECDSA", Format.ASN, true); 659 } 660 661 @Test testSecp256k1Sha3_256()662 public void testSecp256k1Sha3_256 () throws Exception { 663 testVerification("ecdsa_secp256k1_sha3_256_test.json", "ECDSA", Format.ASN, true); 664 } 665 666 @Test testSecp256k1Sha3_512()667 public void testSecp256k1Sha3_512 () throws Exception { 668 testVerification("ecdsa_secp256k1_sha3_512_test.json", "ECDSA", Format.ASN, true); 669 } 670 671 @Test testSecp384r1Sha3_384()672 public void testSecp384r1Sha3_384 () throws Exception { 673 testVerification("ecdsa_secp384r1_sha3_384_test.json", "ECDSA", Format.ASN, true); 674 } 675 676 @Test testSecp384r1Sha3_512()677 public void testSecp384r1Sha3_512 () throws Exception { 678 testVerification("ecdsa_secp384r1_sha3_512_test.json", "ECDSA", Format.ASN, true); 679 } 680 681 @Test testSecp521r1Sha3_512()682 public void testSecp521r1Sha3_512 () throws Exception { 683 testVerification("ecdsa_secp521r1_sha3_512_test.json", "ECDSA", Format.ASN, true); 684 } 685 686 // jdk11 adds P1363 encoded signatures. 687 @Test testSecp224r1Sha224inP1363Format()688 public void testSecp224r1Sha224inP1363Format() throws Exception { 689 testVerification("ecdsa_secp224r1_sha224_p1363_test.json", "ECDSA", Format.P1363, true); 690 } 691 692 @Test testSecp224r1Sha256inP1363Format()693 public void testSecp224r1Sha256inP1363Format() throws Exception { 694 testVerification("ecdsa_secp224r1_sha256_p1363_test.json", "ECDSA", Format.P1363, true); 695 } 696 697 @Test testSecp224r1Sha512inP1363Format()698 public void testSecp224r1Sha512inP1363Format() throws Exception { 699 testVerification("ecdsa_secp224r1_sha512_p1363_test.json", "ECDSA", Format.P1363, true); 700 } 701 702 @Test testSecp256r1Sha256inP1363Format()703 public void testSecp256r1Sha256inP1363Format() throws Exception { 704 testVerification("ecdsa_secp256r1_sha256_p1363_test.json", "ECDSA", Format.P1363, true); 705 } 706 707 @Test testSecp256r1Sha512inP1363Format()708 public void testSecp256r1Sha512inP1363Format() throws Exception { 709 testVerification("ecdsa_secp256r1_sha512_p1363_test.json", "ECDSA", Format.P1363, true); 710 } 711 712 @Test testSecp384r1Sha384inP1363Format()713 public void testSecp384r1Sha384inP1363Format() throws Exception { 714 testVerification("ecdsa_secp384r1_sha384_p1363_test.json", "ECDSA", Format.P1363, true); 715 } 716 717 @Test testSecp384r1Sha512inP1363Format()718 public void testSecp384r1Sha512inP1363Format() throws Exception { 719 testVerification("ecdsa_secp384r1_sha512_p1363_test.json", "ECDSA", Format.P1363, true); 720 } 721 722 @Test testSecp521r1Sha512inP1363Format()723 public void testSecp521r1Sha512inP1363Format() throws Exception { 724 testVerification("ecdsa_secp521r1_sha512_p1363_test.json", "ECDSA", Format.P1363, true); 725 } 726 727 @Test testSecp256k1Sha256inP1363Format()728 public void testSecp256k1Sha256inP1363Format() throws Exception { 729 testVerification("ecdsa_secp256k1_sha256_p1363_test.json", "ECDSA", Format.P1363, true); 730 } 731 732 @Test testSecp256k1Sha512inP1363Format()733 public void testSecp256k1Sha512inP1363Format() throws Exception { 734 testVerification("ecdsa_secp256k1_sha512_p1363_test.json", "ECDSA", Format.P1363, true); 735 } 736 737 @NoPresubmitTest( 738 providers = {ProviderType.OPENJDK}, 739 bugs = {"b/117643131"} 740 ) 741 @Test testBrainpoolP224r1Sha224inP1363Format()742 public void testBrainpoolP224r1Sha224inP1363Format() throws Exception { 743 testVerification("ecdsa_brainpoolP224r1_sha224_p1363_test.json", "ECDSA", Format.P1363, true); 744 } 745 746 @Test testBrainpoolP256r1Sha256inP1363Format()747 public void testBrainpoolP256r1Sha256inP1363Format() throws Exception { 748 testVerification("ecdsa_brainpoolP256r1_sha256_p1363_test.json", "ECDSA", Format.P1363, true); 749 } 750 751 @Test testBrainpoolP320r1Sha384inP1363Format()752 public void testBrainpoolP320r1Sha384inP1363Format() throws Exception { 753 testVerification("ecdsa_brainpoolP320r1_sha384_p1363_test.json", "ECDSA", Format.P1363, true); 754 } 755 756 @Test testBrainpoolP384r1Sha384inP1363Format()757 public void testBrainpoolP384r1Sha384inP1363Format() throws Exception { 758 testVerification("ecdsa_brainpoolP384r1_sha384_p1363_test.json", "ECDSA", Format.P1363, true); 759 } 760 761 @Test testBrainpoolP512r1Sha512inP1363Format()762 public void testBrainpoolP512r1Sha512inP1363Format() throws Exception { 763 testVerification("ecdsa_brainpoolP512r1_sha512_p1363_test.json", "ECDSA", Format.P1363, true); 764 } 765 766 // Testing RSA PKCS#1 v1.5 signatures. 767 @Test testRsaSigning()768 public void testRsaSigning() throws Exception { 769 testSigning("rsa_sig_gen_misc_test.json", "RSA", Format.RAW, true); 770 } 771 772 @Test testRsaSignatures()773 public void testRsaSignatures() throws Exception { 774 testVerification("rsa_signature_test.json", "RSA", Format.RAW, false); 775 } 776 777 @Test testRsaSignature2048sha224()778 public void testRsaSignature2048sha224() throws Exception { 779 testVerification("rsa_signature_2048_sha224_test.json", "RSA", Format.RAW, false); 780 } 781 782 @Test testRsaSignatures2048sha256()783 public void testRsaSignatures2048sha256() throws Exception { 784 testVerification("rsa_signature_2048_sha256_test.json", "RSA", Format.RAW, false); 785 } 786 787 @Test testRsaSignatures2048sha384()788 public void testRsaSignatures2048sha384() throws Exception { 789 testVerification("rsa_signature_2048_sha384_test.json", "RSA", Format.RAW, false); 790 } 791 792 @Test testRsaSignatures2048sha512()793 public void testRsaSignatures2048sha512() throws Exception { 794 testVerification("rsa_signature_2048_sha512_test.json", "RSA", Format.RAW, false); 795 } 796 797 @Test testRsaSignatures3072sha256()798 public void testRsaSignatures3072sha256() throws Exception { 799 testVerification("rsa_signature_3072_sha256_test.json", "RSA", Format.RAW, false); 800 } 801 802 @Test testRsaSignatures3072sha384()803 public void testRsaSignatures3072sha384() throws Exception { 804 testVerification("rsa_signature_3072_sha384_test.json", "RSA", Format.RAW, false); 805 } 806 807 @Test testRsaSignatures3072sha512()808 public void testRsaSignatures3072sha512() throws Exception { 809 testVerification("rsa_signature_3072_sha512_test.json", "RSA", Format.RAW, false); 810 } 811 812 @Test testRsaSignatures4096sha384()813 public void testRsaSignatures4096sha384() throws Exception { 814 testVerification("rsa_signature_4096_sha384_test.json", "RSA", Format.RAW, false); 815 } 816 817 @Test testRsaSignatures4096sha512()818 public void testRsaSignatures4096sha512() throws Exception { 819 testVerification("rsa_signature_4096_sha512_test.json", "RSA", Format.RAW, false); 820 } 821 822 // RSA signatures with truncated hashes. Tests may be skipped if the provider 823 // does not support the hash. 824 @Test testRsaSignatures2048sha512_224()825 public void testRsaSignatures2048sha512_224() throws Exception { 826 testVerification("rsa_signature_2048_sha512_224_test.json", "RSA", Format.RAW, true); 827 } 828 829 @Test testRsaSignatures2048sha512_256()830 public void testRsaSignatures2048sha512_256() throws Exception { 831 testVerification("rsa_signature_2048_sha512_256_test.json", "RSA", Format.RAW, true); 832 } 833 834 @Test testRsaSignatures3072sha512_256()835 public void testRsaSignatures3072sha512_256() throws Exception { 836 testVerification("rsa_signature_3072_sha512_256_test.json", "RSA", Format.RAW, true); 837 } 838 839 @Test testRsaSignatures4096sha512_256()840 public void testRsaSignatures4096sha512_256() throws Exception { 841 testVerification("rsa_signature_4096_sha512_256_test.json", "RSA", Format.RAW, true); 842 } 843 844 // RSA signatures with SHA-3. Not every provider supports SHA-3. Hence the tests 845 // may be skipped. 846 @Test testRsaSignature2048sha3_224()847 public void testRsaSignature2048sha3_224() throws Exception { 848 testVerification("rsa_signature_2048_sha3_224_test.json", "RSA", Format.RAW, true); 849 } 850 851 @Test testRsaSignatures2048sha3_256()852 public void testRsaSignatures2048sha3_256() throws Exception { 853 testVerification("rsa_signature_2048_sha3_256_test.json", "RSA", Format.RAW, true); 854 } 855 856 @Test testRsaSignatures2048sha3_512()857 public void testRsaSignatures2048sha3_512() throws Exception { 858 testVerification("rsa_signature_2048_sha3_512_test.json", "RSA", Format.RAW, true); 859 } 860 861 @Test testRsaSignatures3072sha3_256()862 public void testRsaSignatures3072sha3_256() throws Exception { 863 testVerification("rsa_signature_3072_sha3_256_test.json", "RSA", Format.RAW, true); 864 } 865 866 @Test testRsaSignatures3072sha3_384()867 public void testRsaSignatures3072sha3_384() throws Exception { 868 testVerification("rsa_signature_3072_sha3_384_test.json", "RSA", Format.RAW, true); 869 } 870 871 @Test testRsaSignatures3072sha3_512()872 public void testRsaSignatures3072sha3_512() throws Exception { 873 testVerification("rsa_signature_3072_sha3_512_test.json", "RSA", Format.RAW, true); 874 } 875 876 // EdDSA 877 @NoPresubmitTest( 878 providers = {ProviderType.BOUNCY_CASTLE}, 879 bugs = {"https://github.com/bcgit/bc-java/issues/508"}) 880 @Test testEd25519Verify()881 public void testEd25519Verify() throws Exception { 882 testVerification("eddsa_test.json", "ED25519", Format.RAW, true); 883 } 884 885 @NoPresubmitTest( 886 providers = {ProviderType.BOUNCY_CASTLE}, 887 bugs = {"https://github.com/bcgit/bc-java/issues/508"}) 888 @Test testEd448Verify()889 public void testEd448Verify() throws Exception { 890 testVerification("ed448_test.json", "ED448", Format.RAW, true); 891 } 892 893 // DSA 894 // Two signature encodings for DSA are tested below: ASN encoded signatures 895 // and P1363 encoded signatures. 896 @ExcludedTest( 897 providers = {ProviderType.CONSCRYPT}, 898 comment = "Conscrypt does not support DSA.") 899 @Test testDsa2048Sha224()900 public void testDsa2048Sha224() throws Exception { 901 testVerification("dsa_2048_224_sha224_test.json", "DSA", Format.ASN, true); 902 } 903 904 // NIST allows 2048-bit DSA keys with either a 224-bit q or a 256-bit q. 905 // In both cases the security level is 112-bit. 906 // Jdk generates DSA keys with a 224-bit q (unless specified). 907 @ExcludedTest( 908 providers = {ProviderType.CONSCRYPT}, 909 comment = "Conscrypt does not support DSA.") 910 @Test testDsa2048JdkSha256()911 public void testDsa2048JdkSha256() throws Exception { 912 testVerification("dsa_2048_224_sha256_test.json", "DSA", Format.ASN, true); 913 } 914 915 // OpenSSL generates DSA keys with a 256-bit q (unless specified). 916 @ExcludedTest( 917 providers = {ProviderType.CONSCRYPT}, 918 comment = "Conscrypt does not support DSA.") 919 @Test testDsa2048Sha256()920 public void testDsa2048Sha256() throws Exception { 921 testVerification("dsa_2048_256_sha256_test.json", "DSA", Format.ASN, true); 922 } 923 924 @ExcludedTest( 925 providers = {ProviderType.CONSCRYPT}, 926 comment = "Conscrypt does not support DSA.") 927 @Test testDsa3072Sha256()928 public void testDsa3072Sha256() throws Exception { 929 testVerification("dsa_3072_256_sha256_test.json", "DSA", Format.ASN, true); 930 } 931 932 // DSA tests using P1363 formated signatures. 933 @ExcludedTest( 934 providers = {ProviderType.CONSCRYPT}, 935 comment = "Conscrypt does not support DSA.") 936 @Test testDsa2048Sha224inP1363Format()937 public void testDsa2048Sha224inP1363Format() throws Exception { 938 testVerification("dsa_2048_224_sha224_p1363_test.json", "DSA", Format.P1363, true); 939 } 940 941 @ExcludedTest( 942 providers = {ProviderType.CONSCRYPT}, 943 comment = "Conscrypt does not support DSA.") 944 @Test testDsa2048JdkSha256inP1363Format()945 public void testDsa2048JdkSha256inP1363Format() throws Exception { 946 testVerification("dsa_2048_224_sha256_p1363_test.json", "DSA", Format.P1363, true); 947 } 948 949 @ExcludedTest( 950 providers = {ProviderType.CONSCRYPT}, 951 comment = "Conscrypt does not support DSA.") 952 @Test testDsa2048Sha256inP1363Format()953 public void testDsa2048Sha256inP1363Format() throws Exception { 954 testVerification("dsa_2048_256_sha256_p1363_test.json", "DSA", Format.P1363, true); 955 } 956 957 @ExcludedTest( 958 providers = {ProviderType.CONSCRYPT}, 959 comment = "Conscrypt does not support DSA.") 960 @Test testDsa3072Sha256inP1363Format()961 public void testDsa3072Sha256inP1363Format() throws Exception { 962 testVerification("dsa_3072_256_sha256_p1363_test.json", "DSA", Format.P1363, true); 963 } 964 965 } 966 967