1 /* |
1 /* |
2 * Copyright (c) 1997, 2015, Oracle and/or its affiliates. All rights reserved. |
2 * Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved. |
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
4 * |
4 * |
5 * This code is free software; you can redistribute it and/or modify it |
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 |
6 * under the terms of the GNU General Public License version 2 only, as |
7 * published by the Free Software Foundation. Oracle designates this |
7 * published by the Free Software Foundation. Oracle designates this |
31 import java.security.cert.X509Certificate; |
31 import java.security.cert.X509Certificate; |
32 import java.util.*; |
32 import java.util.*; |
33 |
33 |
34 import javax.security.auth.x500.X500Principal; |
34 import javax.security.auth.x500.X500Principal; |
35 |
35 |
|
36 import sun.net.util.IPAddressUtil; |
36 import sun.security.util.*; |
37 import sun.security.util.*; |
37 import sun.security.pkcs.PKCS9Attribute; |
38 import sun.security.pkcs.PKCS9Attribute; |
38 |
39 |
39 /** |
40 /** |
40 * This class defines the Name Constraints Extension. |
41 * This class defines the Name Constraints Extension. |
463 } catch (CertificateException ce) { |
465 } catch (CertificateException ce) { |
464 throw new IOException("Unable to extract extensions from " + |
466 throw new IOException("Unable to extract extensions from " + |
465 "certificate: " + ce.getMessage()); |
467 "certificate: " + ce.getMessage()); |
466 } |
468 } |
467 |
469 |
468 // If there are no subjectAlternativeNames, perform the special-case |
|
469 // check where if the subjectName contains any EMAILADDRESS |
|
470 // attributes, they must be checked against RFC822 constraints. |
|
471 // If that passes, we're fine. |
|
472 if (altNames == null) { |
470 if (altNames == null) { |
473 return verifyRFC822SpecialCase(subject); |
471 altNames = new GeneralNames(); |
|
472 |
|
473 // RFC 5280 4.2.1.10: |
|
474 // When constraints are imposed on the rfc822Name name form, |
|
475 // but the certificate does not include a subject alternative name, |
|
476 // the rfc822Name constraint MUST be applied to the attribute of |
|
477 // type emailAddress in the subject distinguished name. |
|
478 for (AVA ava : subject.allAvas()) { |
|
479 ObjectIdentifier attrOID = ava.getObjectIdentifier(); |
|
480 if (attrOID.equals(PKCS9Attribute.EMAIL_ADDRESS_OID)) { |
|
481 String attrValue = ava.getValueString(); |
|
482 if (attrValue != null) { |
|
483 try { |
|
484 altNames.add(new GeneralName( |
|
485 new RFC822Name(attrValue))); |
|
486 } catch (IOException ioe) { |
|
487 continue; |
|
488 } |
|
489 } |
|
490 } |
|
491 } |
|
492 } |
|
493 |
|
494 // If there is no IPAddressName or DNSName in subjectAlternativeNames, |
|
495 // see if the last CN inside subjectName can be used instead. |
|
496 DerValue derValue = subject.findMostSpecificAttribute |
|
497 (X500Name.commonName_oid); |
|
498 String cn = derValue == null ? null : derValue.getAsString(); |
|
499 |
|
500 if (cn != null) { |
|
501 try { |
|
502 if (IPAddressUtil.isIPv4LiteralAddress(cn) || |
|
503 IPAddressUtil.isIPv6LiteralAddress(cn)) { |
|
504 if (!hasNameType(altNames, GeneralNameInterface.NAME_IP)) { |
|
505 altNames.add(new GeneralName(new IPAddressName(cn))); |
|
506 } |
|
507 } else { |
|
508 if (!hasNameType(altNames, GeneralNameInterface.NAME_DNS)) { |
|
509 altNames.add(new GeneralName(new DNSName(cn))); |
|
510 } |
|
511 } |
|
512 } catch (IOException ioe) { |
|
513 // OK, cn is neither IP nor DNS |
|
514 } |
474 } |
515 } |
475 |
516 |
476 // verify each subjectAltName |
517 // verify each subjectAltName |
477 for (int i = 0; i < altNames.size(); i++) { |
518 for (int i = 0; i < altNames.size(); i++) { |
478 GeneralNameInterface altGNI = altNames.get(i).getName(); |
519 GeneralNameInterface altGNI = altNames.get(i).getName(); |
565 } |
615 } |
566 return true; |
616 return true; |
567 } |
617 } |
568 |
618 |
569 /** |
619 /** |
570 * Perform the RFC 822 special case check. We have a certificate |
|
571 * that does not contain any subject alternative names. Check that |
|
572 * any EMAILADDRESS attributes in its subject name conform to these |
|
573 * NameConstraints. |
|
574 * |
|
575 * @param subject the certificate's subject name |
|
576 * @return true if certificate verifies successfully |
|
577 * @throws IOException on error |
|
578 */ |
|
579 public boolean verifyRFC822SpecialCase(X500Name subject) throws IOException { |
|
580 for (AVA ava : subject.allAvas()) { |
|
581 ObjectIdentifier attrOID = ava.getObjectIdentifier(); |
|
582 if (attrOID.equals(PKCS9Attribute.EMAIL_ADDRESS_OID)) { |
|
583 String attrValue = ava.getValueString(); |
|
584 if (attrValue != null) { |
|
585 RFC822Name emailName; |
|
586 try { |
|
587 emailName = new RFC822Name(attrValue); |
|
588 } catch (IOException ioe) { |
|
589 continue; |
|
590 } |
|
591 if (!verify(emailName)) { |
|
592 return(false); |
|
593 } |
|
594 } |
|
595 } |
|
596 } |
|
597 return true; |
|
598 } |
|
599 |
|
600 /** |
|
601 * Clone all objects that may be modified during certificate validation. |
620 * Clone all objects that may be modified during certificate validation. |
602 */ |
621 */ |
603 public Object clone() { |
622 public Object clone() { |
604 try { |
623 try { |
605 NameConstraintsExtension newNCE = |
624 NameConstraintsExtension newNCE = |