1 /* 2 * Copyright (c) 1996, 2018, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package sun.security.provider; 27 28 import java.io.*; 29 import java.util.*; 30 import java.math.BigInteger; 31 import java.nio.ByteBuffer; 32 33 import java.security.*; 34 import java.security.SecureRandom; 35 import java.security.interfaces.*; 36 import java.security.spec.*; 37 38 import sun.security.util.Debug; 39 import sun.security.util.DerValue; 40 import sun.security.util.DerInputStream; 41 import sun.security.util.DerOutputStream; 42 import sun.security.jca.JCAUtil; 43 44 /** 45 * The Digital Signature Standard (using the Digital Signature 46 * Algorithm), as described in fips186-3 of the National Instute of 47 * Standards and Technology (NIST), using SHA digest algorithms 48 * from FIPS180-3. 49 * 50 * This file contains both the signature implementation for the 51 * commonly used SHA1withDSA (DSS), SHA224withDSA, SHA256withDSA, 52 * as well as RawDSA, used by TLS among others. RawDSA expects 53 * the 20 byte SHA-1 digest as input via update rather than the 54 * original data like other signature implementations. 55 * 56 * @author Benjamin Renaud 57 * 58 * @since 1.1 59 * 60 * @see DSAPublicKey 61 * @see DSAPrivateKey 62 */ 63 abstract class DSA extends SignatureSpi { 64 65 /* Are we debugging? */ 66 private static final boolean debug = false; 67 68 /* The number of bits used in exponent blinding */ 69 private static final int BLINDING_BITS = 7; 70 71 /* The constant component of the exponent blinding value */ 72 private static final BigInteger BLINDING_CONSTANT = 73 BigInteger.valueOf(1 << BLINDING_BITS); 74 75 /* The parameter object */ 76 private DSAParams params; 77 78 /* algorithm parameters */ 79 private BigInteger presetP, presetQ, presetG; 80 81 /* The public key, if any */ 82 private BigInteger presetY; 83 84 /* The private key, if any */ 85 private BigInteger presetX; 86 87 /* The RNG used to output a seed for generating k */ 88 private SecureRandom signingRandom; 89 90 /* The message digest object used */ 91 private final MessageDigest md; 92 93 /* The format. true for the IEEE P1363 format. false (default) for ASN.1 */ 94 private final boolean p1363Format; 95 96 /** 97 * Construct a blank DSA object. It must be 98 * initialized before being usable for signing or verifying. 99 */ 100 DSA(MessageDigest md) { 101 this(md, false); 102 } 103 104 /** 105 * Construct a blank DSA object that will use the specified 106 * signature format. {@code p1363Format} should be {@code true} to 107 * use the IEEE P1363 format. If {@code p1363Format} is {@code false}, 108 * the DER-encoded ASN.1 format will used. The DSA object must be 109 * initialized before being usable for signing or verifying. 110 */ 111 DSA(MessageDigest md, boolean p1363Format) { 112 super(); 113 this.md = md; 114 this.p1363Format = p1363Format; 115 } 116 117 private static void checkKey(DSAParams params, int digestLen, String mdAlgo) 118 throws InvalidKeyException { 119 // FIPS186-3 states in sec4.2 that a hash function which provides 120 // a lower security strength than the (L, N) pair ordinarily should 121 // not be used. 122 int valueN = params.getQ().bitLength(); 123 if (valueN > digestLen) { 124 throw new InvalidKeyException("The security strength of " + 125 mdAlgo + " digest algorithm is not sufficient for this key size"); 126 } 127 } 128 129 /** 130 * Initialize the DSA object with a DSA private key. 131 * 132 * @param privateKey the DSA private key 133 * 134 * @exception InvalidKeyException if the key is not a valid DSA private 135 * key. 136 */ 137 protected void engineInitSign(PrivateKey privateKey) 138 throws InvalidKeyException { 139 if (!(privateKey instanceof java.security.interfaces.DSAPrivateKey)) { 140 throw new InvalidKeyException("not a DSA private key: " + 141 privateKey); 142 } 143 144 java.security.interfaces.DSAPrivateKey priv = 145 (java.security.interfaces.DSAPrivateKey)privateKey; 146 147 // check for algorithm specific constraints before doing initialization 148 DSAParams params = priv.getParams(); 149 if (params == null) { 150 throw new InvalidKeyException("DSA private key lacks parameters"); 151 } 152 153 // check key size against hash output size for signing 154 // skip this check for verification to minimize impact on existing apps 155 if (!"NullDigest20".equals(md.getAlgorithm())) { 156 checkKey(params, md.getDigestLength()*8, md.getAlgorithm()); 157 } 158 159 this.params = params; 160 this.presetX = priv.getX(); 161 this.presetY = null; 162 this.presetP = params.getP(); 163 this.presetQ = params.getQ(); 164 this.presetG = params.getG(); 165 this.md.reset(); 166 } 167 /** 168 * Initialize the DSA object with a DSA public key. 169 * 170 * @param publicKey the DSA public key. 171 * 172 * @exception InvalidKeyException if the key is not a valid DSA public 173 * key. 174 */ 175 protected void engineInitVerify(PublicKey publicKey) 176 throws InvalidKeyException { 177 if (!(publicKey instanceof java.security.interfaces.DSAPublicKey)) { 178 throw new InvalidKeyException("not a DSA public key: " + 179 publicKey); 180 } 181 java.security.interfaces.DSAPublicKey pub = 182 (java.security.interfaces.DSAPublicKey)publicKey; 183 184 // check for algorithm specific constraints before doing initialization 185 DSAParams params = pub.getParams(); 186 if (params == null) { 187 throw new InvalidKeyException("DSA public key lacks parameters"); 188 } 189 this.params = params; 190 this.presetY = pub.getY(); 191 this.presetX = null; 192 this.presetP = params.getP(); 193 this.presetQ = params.getQ(); 194 this.presetG = params.getG(); 195 this.md.reset(); 196 } 197 198 /** 199 * Update a byte to be signed or verified. 200 */ 201 protected void engineUpdate(byte b) { 202 md.update(b); 203 } 204 205 /** 206 * Update an array of bytes to be signed or verified. 207 */ 208 protected void engineUpdate(byte[] data, int off, int len) { 209 md.update(data, off, len); 210 } 211 212 protected void engineUpdate(ByteBuffer b) { 213 md.update(b); 214 } 215 216 217 /** 218 * Sign all the data thus far updated. The signature format is 219 * determined by {@code p1363Format}. If {@code p1363Format} is 220 * {@code false} (the default), then the signature is formatted 221 * according to the Canonical Encoding Rules, returned as a DER 222 * sequence of Integers, r and s. If {@code p1363Format} is 223 * {@code false}, the signature is returned in the IEEE P1363 224 * format, which is the concatenation or r and s. 225 * 226 * @return a signature block formatted according to the format 227 * indicated by {@code p1363Format} 228 * 229 * @exception SignatureException if the signature object was not 230 * properly initialized, or if another exception occurs. 231 * 232 * @see sun.security.DSA#engineUpdate 233 * @see sun.security.DSA#engineVerify 234 */ 235 protected byte[] engineSign() throws SignatureException { 236 BigInteger k = generateK(presetQ); 237 BigInteger r = generateR(presetP, presetQ, presetG, k); 238 BigInteger s = generateS(presetX, presetQ, r, k); 239 240 if (p1363Format) { 241 // Return the concatenation of r and s 242 byte[] rBytes = r.toByteArray(); 243 byte[] sBytes = s.toByteArray(); 244 245 int size = presetQ.bitLength() / 8; 246 byte[] outseq = new byte[size * 2]; 247 248 int rLength = rBytes.length; 249 int sLength = sBytes.length; 250 int i; 251 for (i = rLength; i > 0 && rBytes[rLength - i] == 0; i--); 252 253 int j; 254 for (j = sLength; 255 j > 0 && sBytes[sLength - j] == 0; j--); 256 257 System.arraycopy(rBytes, rLength - i, outseq, size - i, i); 258 System.arraycopy(sBytes, sLength - j, outseq, size * 2 - j, j); 259 260 return outseq; 261 } else { 262 // Return the DER-encoded ASN.1 form 263 try { 264 DerOutputStream outseq = new DerOutputStream(100); 265 outseq.putInteger(r); 266 outseq.putInteger(s); 267 DerValue result = new DerValue(DerValue.tag_Sequence, 268 outseq.toByteArray()); 269 270 return result.toByteArray(); 271 272 } catch (IOException e) { 273 throw new SignatureException("error encoding signature"); 274 } 275 } 276 } 277 278 /** 279 * Verify all the data thus far updated. 280 * 281 * @param signature the alleged signature, encoded using the 282 * Canonical Encoding Rules, as a sequence of integers, r and s. 283 * 284 * @exception SignatureException if the signature object was not 285 * properly initialized, or if another exception occurs. 286 * 287 * @see sun.security.DSA#engineUpdate 288 * @see sun.security.DSA#engineSign 289 */ 290 protected boolean engineVerify(byte[] signature) 291 throws SignatureException { 292 return engineVerify(signature, 0, signature.length); 293 } 294 295 /** 296 * Verify all the data thus far updated. 297 * 298 * @param signature the alleged signature, encoded using the 299 * format indicated by {@code p1363Format}. If {@code p1363Format} 300 * is {@code false} (the default), then the signature is formatted 301 * according to the Canonical Encoding Rules, as a DER sequence of 302 * Integers, r and s. If {@code p1363Format} is {@code false}, 303 * the signature is in the IEEE P1363 format, which is the 304 * concatenation or r and s. 305 * 306 * @param offset the offset to start from in the array of bytes. 307 * 308 * @param length the number of bytes to use, starting at offset. 309 * 310 * @exception SignatureException if the signature object was not 311 * properly initialized, or if another exception occurs. 312 * 313 * @see sun.security.DSA#engineUpdate 314 * @see sun.security.DSA#engineSign 315 */ 316 protected boolean engineVerify(byte[] signature, int offset, int length) 317 throws SignatureException { 318 319 BigInteger r = null; 320 BigInteger s = null; 321 322 if (p1363Format) { 323 if ((length & 1) == 1) { 324 // length of signature byte array should be even 325 throw new SignatureException("invalid signature format"); 326 } 327 int mid = length/2; 328 r = new BigInteger(Arrays.copyOfRange(signature, 0, mid)); 329 s = new BigInteger(Arrays.copyOfRange(signature, mid, length)); 330 } else { 331 // first decode the signature. 332 try { 333 // Enforce strict DER checking for signatures 334 DerInputStream in = 335 new DerInputStream(signature, offset, length, false); 336 DerValue[] values = in.getSequence(2); 337 338 // check number of components in the read sequence 339 // and trailing data 340 if ((values.length != 2) || (in.available() != 0)) { 341 throw new IOException("Invalid encoding for signature"); 342 } 343 r = values[0].getBigInteger(); 344 s = values[1].getBigInteger(); 345 } catch (IOException e) { 346 throw new SignatureException("Invalid encoding for signature", e); 347 } 348 } 349 350 // some implementations do not correctly encode values in the ASN.1 351 // 2's complement format. force r and s to be positive in order to 352 // to validate those signatures 353 if (r.signum() < 0) { 354 r = new BigInteger(1, r.toByteArray()); 355 } 356 if (s.signum() < 0) { 357 s = new BigInteger(1, s.toByteArray()); 358 } 359 360 if ((r.compareTo(presetQ) == -1) && (s.compareTo(presetQ) == -1)) { 361 BigInteger w = generateW(presetP, presetQ, presetG, s); 362 BigInteger v = generateV(presetY, presetP, presetQ, presetG, w, r); 363 return v.equals(r); 364 } else { 365 throw new SignatureException("invalid signature: out of range values"); 366 } 367 } 368 369 @Deprecated 370 protected void engineSetParameter(String key, Object param) { 371 throw new InvalidParameterException("No parameter accepted"); 372 } 373 374 @Override 375 protected void engineSetParameter(AlgorithmParameterSpec params) 376 throws InvalidAlgorithmParameterException { 377 if (params != null) { 378 throw new InvalidAlgorithmParameterException("No parameter accepted"); 379 } 380 } 381 382 @Deprecated 383 protected Object engineGetParameter(String key) { 384 return null; 385 } 386 387 @Override 388 protected AlgorithmParameters engineGetParameters() { 389 return null; 390 } 391 392 393 private BigInteger generateR(BigInteger p, BigInteger q, BigInteger g, 394 BigInteger k) { 395 396 // exponent blinding to hide information from timing channel 397 SecureRandom random = getSigningRandom(); 398 // start with a random blinding component 399 BigInteger blindingValue = new BigInteger(BLINDING_BITS, random); 400 // add the fixed blinding component 401 blindingValue = blindingValue.add(BLINDING_CONSTANT); 402 // replace k with a blinded value that is congruent (mod q) 403 k = k.add(q.multiply(blindingValue)); 404 405 BigInteger temp = g.modPow(k, p); 406 return temp.mod(q); 407 } 408 409 private BigInteger generateS(BigInteger x, BigInteger q, 410 BigInteger r, BigInteger k) throws SignatureException { 411 412 byte[] s2; 413 try { 414 s2 = md.digest(); 415 } catch (RuntimeException re) { 416 // Only for RawDSA due to its 20-byte length restriction 417 throw new SignatureException(re.getMessage()); 418 } 419 // get the leftmost min(N, outLen) bits of the digest value 420 int nBytes = q.bitLength()/8; 421 if (nBytes < s2.length) { 422 s2 = Arrays.copyOfRange(s2, 0, nBytes); 423 } 424 BigInteger z = new BigInteger(1, s2); 425 BigInteger k1 = k.modInverse(q); 426 427 return x.multiply(r).add(z).multiply(k1).mod(q); 428 } 429 430 private BigInteger generateW(BigInteger p, BigInteger q, 431 BigInteger g, BigInteger s) { 432 return s.modInverse(q); 433 } 434 435 private BigInteger generateV(BigInteger y, BigInteger p, 436 BigInteger q, BigInteger g, BigInteger w, BigInteger r) 437 throws SignatureException { 438 439 byte[] s2; 440 try { 441 s2 = md.digest(); 442 } catch (RuntimeException re) { 443 // Only for RawDSA due to its 20-byte length restriction 444 throw new SignatureException(re.getMessage()); 445 } 446 // get the leftmost min(N, outLen) bits of the digest value 447 int nBytes = q.bitLength()/8; 448 if (nBytes < s2.length) { 449 s2 = Arrays.copyOfRange(s2, 0, nBytes); 450 } 451 BigInteger z = new BigInteger(1, s2); 452 453 BigInteger u1 = z.multiply(w).mod(q); 454 BigInteger u2 = (r.multiply(w)).mod(q); 455 456 BigInteger t1 = g.modPow(u1,p); 457 BigInteger t2 = y.modPow(u2,p); 458 BigInteger t3 = t1.multiply(t2); 459 BigInteger t5 = t3.mod(p); 460 return t5.mod(q); 461 } 462 463 protected BigInteger generateK(BigInteger q) { 464 // Implementation defined in FIPS 186-4 AppendixB.2.1. 465 SecureRandom random = getSigningRandom(); 466 byte[] kValue = new byte[(q.bitLength() + 7)/8 + 8]; 467 468 random.nextBytes(kValue); 469 return new BigInteger(1, kValue).mod( 470 q.subtract(BigInteger.ONE)).add(BigInteger.ONE); 471 } 472 473 // Use the application-specified SecureRandom Object if provided. 474 // Otherwise, use our default SecureRandom Object. 475 protected SecureRandom getSigningRandom() { 476 if (signingRandom == null) { 477 if (appRandom != null) { 478 signingRandom = appRandom; 479 } else { 480 signingRandom = JCAUtil.getSecureRandom(); 481 } 482 } 483 return signingRandom; 484 } 485 486 /** 487 * Return a human readable rendition of the engine. 488 */ 489 public String toString() { 490 String printable = "DSA Signature"; 491 if (presetP != null && presetQ != null && presetG != null) { 492 printable += "\n\tp: " + Debug.toHexString(presetP); 493 printable += "\n\tq: " + Debug.toHexString(presetQ); 494 printable += "\n\tg: " + Debug.toHexString(presetG); 495 } else { 496 printable += "\n\t P, Q or G not initialized."; 497 } 498 if (presetY != null) { 499 printable += "\n\ty: " + Debug.toHexString(presetY); 500 } 501 if (presetY == null && presetX == null) { 502 printable += "\n\tUNINIIALIZED"; 503 } 504 return printable; 505 } 506 507 /** 508 * Standard SHA224withDSA implementation as defined in FIPS186-3. 509 */ 510 public static final class SHA224withDSA extends DSA { 511 public SHA224withDSA() throws NoSuchAlgorithmException { 512 super(MessageDigest.getInstance("SHA-224")); 513 } 514 } 515 516 /** 517 * SHA224withDSA implementation that uses the IEEE P1363 format. 518 */ 519 public static final class SHA224withDSAinP1363Format extends DSA { 520 public SHA224withDSAinP1363Format() throws NoSuchAlgorithmException { 521 super(MessageDigest.getInstance("SHA-224"), true); 522 } 523 } 524 525 /** 526 * Standard SHA256withDSA implementation as defined in FIPS186-3. 527 */ 528 public static final class SHA256withDSA extends DSA { 529 public SHA256withDSA() throws NoSuchAlgorithmException { 530 super(MessageDigest.getInstance("SHA-256")); 531 } 532 } 533 534 /** 535 * SHA256withDSA implementation that uses the IEEE P1363 format. 536 */ 537 public static final class SHA256withDSAinP1363Format extends DSA { 538 public SHA256withDSAinP1363Format() throws NoSuchAlgorithmException { 539 super(MessageDigest.getInstance("SHA-256"), true); 540 } 541 } 542 543 /** 544 * Standard SHA1withDSA implementation. 545 */ 546 public static final class SHA1withDSA extends DSA { 547 public SHA1withDSA() throws NoSuchAlgorithmException { 548 super(MessageDigest.getInstance("SHA-1")); 549 } 550 } 551 552 /** 553 * SHA1withDSA implementation that uses the IEEE P1363 format. 554 */ 555 public static final class SHA1withDSAinP1363Format extends DSA { 556 public SHA1withDSAinP1363Format() throws NoSuchAlgorithmException { 557 super(MessageDigest.getInstance("SHA-1"), true); 558 } 559 } 560 561 /** 562 * Raw DSA. 563 * 564 * Raw DSA requires the data to be exactly 20 bytes long. If it is 565 * not, a SignatureException is thrown when sign()/verify() is called 566 * per JCA spec. 567 */ 568 static class Raw extends DSA { 569 // Internal special-purpose MessageDigest impl for RawDSA 570 // Only override whatever methods used 571 // NOTE: no clone support 572 public static final class NullDigest20 extends MessageDigest { 573 // 20 byte digest buffer 574 private final byte[] digestBuffer = new byte[20]; 575 576 // offset into the buffer; use Integer.MAX_VALUE to indicate 577 // out-of-bound condition 578 private int ofs = 0; 579 580 protected NullDigest20() { 581 super("NullDigest20"); 582 } 583 protected void engineUpdate(byte input) { 584 if (ofs == digestBuffer.length) { 585 ofs = Integer.MAX_VALUE; 586 } else { 587 digestBuffer[ofs++] = input; 588 } 589 } 590 protected void engineUpdate(byte[] input, int offset, int len) { 591 if (len > (digestBuffer.length - ofs)) { 592 ofs = Integer.MAX_VALUE; 593 } else { 594 System.arraycopy(input, offset, digestBuffer, ofs, len); 595 ofs += len; 596 } 597 } 598 protected final void engineUpdate(ByteBuffer input) { 599 int inputLen = input.remaining(); 600 if (inputLen > (digestBuffer.length - ofs)) { 601 ofs = Integer.MAX_VALUE; 602 } else { 603 input.get(digestBuffer, ofs, inputLen); 604 ofs += inputLen; 605 } 606 } 607 protected byte[] engineDigest() throws RuntimeException { 608 if (ofs != digestBuffer.length) { 609 throw new RuntimeException 610 ("Data for RawDSA must be exactly 20 bytes long"); 611 } 612 reset(); 613 return digestBuffer; 614 } 615 protected int engineDigest(byte[] buf, int offset, int len) 616 throws DigestException { 617 if (ofs != digestBuffer.length) { 618 throw new DigestException 619 ("Data for RawDSA must be exactly 20 bytes long"); 620 } 621 if (len < digestBuffer.length) { 622 throw new DigestException 623 ("Output buffer too small; must be at least 20 bytes"); 624 } 625 System.arraycopy(digestBuffer, 0, buf, offset, digestBuffer.length); 626 reset(); 627 return digestBuffer.length; 628 } 629 630 protected void engineReset() { 631 ofs = 0; 632 } 633 protected final int engineGetDigestLength() { 634 return digestBuffer.length; 635 } 636 } 637 638 private Raw(boolean p1363Format) throws NoSuchAlgorithmException { 639 super(new NullDigest20(), p1363Format); 640 } 641 642 } 643 644 /** 645 * Standard Raw DSA implementation. 646 */ 647 public static final class RawDSA extends Raw { 648 public RawDSA() throws NoSuchAlgorithmException { 649 super(false); 650 } 651 } 652 653 /** 654 * Raw DSA implementation that uses the IEEE P1363 format. 655 */ 656 public static final class RawDSAinP1363Format extends Raw { 657 public RawDSAinP1363Format() throws NoSuchAlgorithmException { 658 super(true); 659 } 660 } 661 }