OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-dev/] [or1k-gcc/] [libjava/] [classpath/] [java/] [security/] [cert/] [X509CertSelector.java] - Blame information for rev 771

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 771 jeremybenn
/* X509CertSelector.java -- selects X.509 certificates by criteria.
2
   Copyright (C) 2004, 2005, 2006 Free Software Foundation, Inc.
3
 
4
This file is part of GNU Classpath.
5
 
6
GNU Classpath is free software; you can redistribute it and/or modify
7
it under the terms of the GNU General Public License as published by
8
the Free Software Foundation; either version 2, or (at your option)
9
any later version.
10
 
11
GNU Classpath is distributed in the hope that it will be useful, but
12
WITHOUT ANY WARRANTY; without even the implied warranty of
13
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
General Public License for more details.
15
 
16
You should have received a copy of the GNU General Public License
17
along with GNU Classpath; see the file COPYING.  If not, write to the
18
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19
02110-1301 USA.
20
 
21
Linking this library statically or dynamically with other modules is
22
making a combined work based on this library.  Thus, the terms and
23
conditions of the GNU General Public License cover the whole
24
combination.
25
 
26
As a special exception, the copyright holders of this library give you
27
permission to link this library with independent modules to produce an
28
executable, regardless of the license terms of these independent
29
modules, and to copy and distribute the resulting executable under
30
terms of your choice, provided that you also meet, for each linked
31
independent module, the terms and conditions of the license of that
32
module.  An independent module is a module which is not derived from
33
or based on this library.  If you modify this library, you may extend
34
this exception to your version of the library, but you are not
35
obligated to do so.  If you do not wish to do so, delete this
36
exception statement from your version. */
37
 
38
 
39
package java.security.cert;
40
 
41
import gnu.classpath.SystemProperties;
42
import gnu.java.lang.CPStringBuilder;
43
import gnu.java.security.OID;
44
import gnu.java.security.x509.GnuPKIExtension;
45
import gnu.java.security.x509.ext.CertificatePolicies;
46
import gnu.java.security.x509.ext.Extension;
47
import gnu.java.security.x509.ext.GeneralName;
48
import gnu.java.security.x509.ext.GeneralSubtree;
49
import gnu.java.security.x509.ext.NameConstraints;
50
import gnu.java.security.x509.ext.GeneralName.Kind;
51
 
52
import java.io.IOException;
53
import java.math.BigInteger;
54
import java.net.InetAddress;
55
import java.security.KeyFactory;
56
import java.security.PublicKey;
57
import java.security.spec.X509EncodedKeySpec;
58
import java.util.ArrayList;
59
import java.util.Arrays;
60
import java.util.Collection;
61
import java.util.Collections;
62
import java.util.Date;
63
import java.util.HashSet;
64
import java.util.Iterator;
65
import java.util.LinkedList;
66
import java.util.List;
67
import java.util.Set;
68
 
69
import javax.security.auth.x500.X500Principal;
70
 
71
/**
72
 * A concrete implementation of {@link CertSelector} for X.509 certificates,
73
 * which allows a number of criteria to be set when accepting certificates,
74
 * from validity dates, to issuer and subject distinguished names, to some
75
 * of the various X.509 extensions.
76
 *
77
 * <p>Use of this class requires extensive knowledge of the Internet
78
 * Engineering Task Force's Public Key Infrastructure (X.509). The primary
79
 * document describing this standard is <a
80
 * href="http://www.ietf.org/rfc/rfc3280.txt">RFC 3280: Internet X.509
81
 * Public Key Infrastructure Certificate and Certificate Revocation List
82
 * (CRL) Profile</a>.
83
 *
84
 * <p>Note that this class is not thread-safe. If multiple threads will
85
 * use or modify this class then they need to synchronize on the object.
86
 *
87
 * @author Casey Marshall (csm@gnu.org)
88
 * @since 1.4
89
 */
90
public class X509CertSelector implements CertSelector, Cloneable
91
{
92
 
93
  // Constants and fields.
94
  // -------------------------------------------------------------------------
95
 
96
  private static final String AUTH_KEY_ID = "2.5.29.35";
97
  private static final String SUBJECT_KEY_ID = "2.5.29.14";
98
  private static final String NAME_CONSTRAINTS_ID = "2.5.29.30";
99
 
100
  private static boolean checkOid(int[] oid)
101
  {
102
    return (oid != null && oid.length > 2 &&
103
            (oid[0] >= 0 && oid[0] <= 2) && (oid[1] >= 0 && oid[1] <= 39));
104
  }
105
 
106
  private static GeneralName makeName(int id, String name) throws IOException
107
  {
108
    byte[] nameBytes = null;
109
    GeneralName.Kind kind = GeneralName.Kind.forTag(id);
110
    switch (Kind.forTag(id))
111
    {
112
      case dNSName:
113
      case rfc822Name:
114
      case uniformResourceIdentifier:
115
        nameBytes = name.getBytes("ASCII");
116
        break;
117
 
118
      case iPAddress:
119
        InetAddress addr = InetAddress.getByName(name);
120
        nameBytes = addr.getAddress();
121
        break;
122
 
123
      case registeredId:
124
        OID oid = new OID(name);
125
        nameBytes = oid.getDER();
126
        break;
127
 
128
      case directoryName:
129
        X500Principal xname = new X500Principal(name);
130
        nameBytes = xname.getEncoded();
131
        break;
132
 
133
      case ediPartyName:
134
      case x400Address:
135
      case otherName:
136
        throw new IOException("cannot decode string representation of "
137
                              + kind);
138
    }
139
    return new GeneralName(kind, nameBytes);
140
  }
141
 
142
  private int basicConstraints;
143
  private X509Certificate cert;
144
  private BigInteger serialNo;
145
  private X500Principal issuer;
146
  private X500Principal subject;
147
  private byte[] subjectKeyId;
148
  private byte[] authKeyId;
149
  private boolean[] keyUsage;
150
  private Date certValid;
151
  private OID sigId;
152
  private PublicKey subjectKey;
153
  private X509EncodedKeySpec subjectKeySpec;
154
  private Set<String> keyPurposeSet;
155
  private List<GeneralName> altNames;
156
  private boolean matchAllNames;
157
  private byte[] nameConstraints;
158
  private Set<OID> policy;
159
  private List<GeneralName> pathToNames;
160
 
161
  /**
162
   * Creates a new X.509 certificate selector. The new selector will be
163
   * empty, and will accept any certificate (provided that it is an
164
   * {@link X509Certificate}).
165
   */
166
  public X509CertSelector()
167
  {
168
    basicConstraints = -1;
169
  }
170
 
171
  /**
172
   * Add a name to match in the NameConstraints extension. The argument is
173
   * the DER-encoded bytes of a GeneralName structure.
174
   *
175
   * See the method {@link #addSubjectAlternativeName(int, byte[])} for the
176
   * format of the GeneralName structure.
177
   *
178
   * @param id The name identifier. Must be between 0 and 8.
179
   * @param name The DER-encoded bytes of the name to match.
180
   * @throws IOException If the name DER is malformed.
181
   */
182
  public void addPathToName(int id, byte[] name) throws IOException
183
  {
184
    GeneralName generalName = new GeneralName(GeneralName.Kind.forTag(id), name);
185
    if (pathToNames == null)
186
      pathToNames = new LinkedList<GeneralName>();
187
    pathToNames.add(generalName);
188
  }
189
 
190
  /**
191
   * Add a name to match in the NameConstraints extension. This method will
192
   * only recognize certain types of name that have convenient string
193
   * encodings. For robustness, you should use the {@link
194
   *  #addPathToName(int, byte[])} method whenever possible.
195
   *
196
   * @param id The name identifier. Must be between 0 and 8.
197
   * @param name The name.
198
   * @throws IOException If the name cannot be decoded.
199
   */
200
  public void addPathToName(int id, String name) throws IOException
201
  {
202
    GeneralName generalName = makeName(id, name);
203
    if (pathToNames == null)
204
      pathToNames = new LinkedList<GeneralName>();
205
    pathToNames.add(generalName);
206
  }
207
 
208
  /**
209
   * Add a name, as DER-encoded bytes, to the subject alternative names
210
   * criterion.
211
   *
212
   * The name is a GeneralName structure, which has the ASN.1 format:
213
   *
214
   * <pre>
215
  GeneralName ::= CHOICE {
216
    otherName                       [0]     OtherName,
217
    rfc822Name                      [1]     IA5String,
218
    dNSName                         [2]     IA5String,
219
    x400Address                     [3]     ORAddress,
220
    directoryName                   [4]     Name,
221
    ediPartyName                    [5]     EDIPartyName,
222
    uniformResourceIdentifier       [6]     IA5String,
223
    iPAddress                       [7]     OCTET STRING,
224
    registeredID                    [8]     OBJECT IDENTIFIER }
225
</pre>
226
   *
227
   * @param id The type of name this is.
228
   * @param name The DER-encoded name.
229
   * @throws IOException If the name is not a valid DER sequence.
230
   */
231
  public void addSubjectAlternativeName(int id, byte[] name)
232
    throws IOException
233
  {
234
    GeneralName generalName = new GeneralName(GeneralName.Kind.forTag(id), name);
235
    if (altNames == null)
236
      altNames = new LinkedList<GeneralName>();
237
    altNames.add(generalName);
238
  }
239
 
240
  /**
241
   * Add a name to the subject alternative names criterion. This method will
242
   * only recognize certain types of name that have convenient string
243
   * encodings. For robustness, you should use the {@link
244
   *  #addSubjectAlternativeName(int, byte[])} method whenever possible.
245
   *
246
   * This method can only decode certain name kinds of names as strings.
247
   *
248
   * @param id The type of name this is. Must be in the range [0,8].
249
   * @param name The name.
250
   * @throws IOException If the id is out of range, or if the name
251
   *   is null.
252
   */
253
  public void addSubjectAlternativeName(int id, String name)
254
    throws IOException
255
  {
256
    GeneralName generalName = makeName(id, name);
257
    if (altNames == null)
258
      altNames = new LinkedList<GeneralName>();
259
    altNames.add(generalName);
260
  }
261
 
262
  public Object clone()
263
  {
264
    try
265
      {
266
        return super.clone();
267
      }
268
    catch (CloneNotSupportedException shouldNotHappen)
269
      {
270
        throw new Error(shouldNotHappen);
271
      }
272
  }
273
 
274
  /**
275
   * Returns the authority key identifier criterion, or <code>null</code> if
276
   * this value was not set. Note that the byte array is cloned to prevent
277
   * modification.
278
   *
279
   * @return The authority key identifier.
280
   */
281
  public byte[] getAuthorityKeyIdentifier()
282
  {
283
    if (authKeyId != null)
284
      return (byte[]) authKeyId.clone();
285
    else
286
      return null;
287
  }
288
 
289
  /**
290
   * Returns the basic constraints criterion, or -1 if this value is not set.
291
   *
292
   * @return The basic constraints.
293
   */
294
  public int getBasicConstraints()
295
  {
296
    return basicConstraints;
297
  }
298
 
299
  /**
300
   * Returns the certificate criterion, or <code>null</code> if this value
301
   * was not set.
302
   *
303
   * @return The certificate.
304
   */
305
  public X509Certificate getCertificate()
306
  {
307
    return cert;
308
  }
309
 
310
  /**
311
   * Returns the date at which certificates must be valid, or <code>null</code>
312
   * if this criterion was not set.
313
   *
314
   * @return The target certificate valitity date.
315
   */
316
  public Date getCertificateValid()
317
  {
318
    if (certValid != null)
319
      return (Date) certValid.clone();
320
    else
321
      return null;
322
  }
323
 
324
  /**
325
   * Returns the set of extended key purpose IDs, as an unmodifiable set
326
   * of OID strings. Returns <code>null</code> if this criterion is not
327
   * set.
328
   *
329
   * @return The set of key purpose OIDs (strings).
330
   */
331
  public Set<String> getExtendedKeyUsage()
332
  {
333
    if (keyPurposeSet != null)
334
      return Collections.unmodifiableSet(keyPurposeSet);
335
    else
336
      return null;
337
  }
338
 
339
  /**
340
   * Returns the issuer criterion as a sequence of DER bytes, or
341
   * <code>null</code> if this value was not set.
342
   *
343
   * @return The issuer.
344
   */
345
  public byte[] getIssuerAsBytes() throws IOException
346
  {
347
    if (issuer != null)
348
      return issuer.getEncoded();
349
    else
350
      return null;
351
  }
352
 
353
  /**
354
   * Returns the issuer criterion as a string, or <code>null</code> if this
355
   * value was not set.
356
   *
357
   * @return The issuer.
358
   */
359
  public String getIssuerAsString()
360
  {
361
    if (issuer != null)
362
      return issuer.getName();
363
    else
364
      return null;
365
  }
366
 
367
  /**
368
   * Returns the public key usage criterion, or <code>null</code> if this
369
   * value is not set. Note that the array is cloned to prevent modification.
370
   *
371
   * @return The public key usage.
372
   */
373
  public boolean[] getKeyUsage()
374
  {
375
    if (keyUsage != null)
376
      return (boolean[]) keyUsage.clone();
377
    else
378
      return null;
379
  }
380
 
381
  /**
382
   * Returns whether or not all specified alternative names must match.
383
   * If false, a certificate is considered a match if <em>one</em> of the
384
   * specified alternative names matches.
385
   *
386
   * @return true if all names must match.
387
   */
388
  public boolean getMatchAllSubjectAltNames()
389
  {
390
    return matchAllNames;
391
  }
392
 
393
  /**
394
   * Returns the name constraints criterion, or <code>null</code> if this
395
   * value is not set. Note that the byte array is cloned to prevent
396
   * modification.
397
   *
398
   * @return The name constraints.
399
   */
400
  public byte[] getNameConstraints()
401
  {
402
    if (nameConstraints != null)
403
      return (byte[]) nameConstraints.clone();
404
    else
405
      return null;
406
  }
407
 
408
  public Collection<List<?>> getPathToNames()
409
  {
410
    if (pathToNames != null)
411
      {
412
        List<List<?>> names = new ArrayList<List<?>>(pathToNames.size());
413
        for (GeneralName name : pathToNames)
414
          {
415
            List<Object> n = new ArrayList<Object>(2);
416
            n.add(name.kind().tag());
417
            n.add(name.name());
418
            names.add(n);
419
          }
420
 
421
        return names;
422
      }
423
    return null;
424
  }
425
 
426
  /**
427
   * Returns the certificate policy extension that will be matched by this
428
   * selector, or null if the certificate policy will not be matched.
429
   *
430
   * @return The policy to be matched, or null.
431
   */
432
  public Set<String> getPolicy()
433
  {
434
    Set<OID> p = this.policy;
435
    if (p != null)
436
      {
437
        Set<String> strings = new HashSet<String>(p.size());
438
        for (OID o : p)
439
          {
440
            strings.add(o.toString());
441
          }
442
        return strings;
443
      }
444
    return null;
445
  }
446
 
447
  /**
448
   * This method, and its related X.509 certificate extension &mdash; the
449
   * private key usage period &mdash; is not supported under the Internet
450
   * PKI for X.509 certificates (PKIX), described in RFC 3280. As such, this
451
   * method is not supported either.
452
   *
453
   * <p>Do not use this method. It is not deprecated, as it is not deprecated
454
   * in the Java standard, but it is basically a no-operation and simply
455
   * returns <code>null</code>.
456
   *
457
   * @return Null.
458
   */
459
  public Date getPrivateKeyValid()
460
  {
461
    return null;
462
  }
463
 
464
  /**
465
   * Returns the serial number criterion, or <code>null</code> if this
466
   * value was not set.
467
   *
468
   * @return The serial number.
469
   */
470
  public BigInteger getSerialNumber()
471
  {
472
    return serialNo;
473
  }
474
 
475
  /**
476
   * Get the subject alternative names criterion. The collection returned
477
   * is a collection of pairs: the first element is an {@link Integer}
478
   * containing the name type, and the second is a byte array containing
479
   * the DER-encoded name bytes.
480
   *
481
   * @return The subject alternative names criterion. Returns null if this
482
   *  criterion is not set.
483
   */
484
  public Collection<List<?>> getSubjectAlternativeNames()
485
  {
486
    if (altNames != null)
487
      {
488
        List<List<?>> names = new ArrayList<List<?>>(altNames.size());
489
        for (GeneralName name : altNames)
490
          {
491
            List<Object> n = new ArrayList<Object>(2);
492
            n.add(name.kind().tag());
493
            n.add(name.name());
494
            names.add(n);
495
          }
496
        return names;
497
      }
498
    return null;
499
  }
500
 
501
  /**
502
   * Returns the subject criterion as a sequence of DER bytes, or
503
   * <code>null</code> if this value is not set.
504
   *
505
   * @return The subject.
506
   */
507
  public byte[] getSubjectAsBytes() throws IOException
508
  {
509
    if (subject != null)
510
      return subject.getEncoded();
511
    else
512
      return null;
513
  }
514
 
515
  /**
516
   * Returns the subject criterion as a string, of <code>null</code> if
517
   * this value was not set.
518
   *
519
   * @return The subject.
520
   */
521
  public String getSubjectAsString()
522
  {
523
    if (subject != null)
524
      return subject.getName();
525
    else
526
      return null;
527
  }
528
 
529
  /**
530
   * Returns the subject key identifier criterion, or <code>null</code> if
531
   * this value was not set. Note that the byte array is cloned to prevent
532
   * modification.
533
   *
534
   * @return The subject key identifier.
535
   */
536
  public byte[] getSubjectKeyIdentifier()
537
  {
538
    if (subjectKeyId != null)
539
      return (byte[]) subjectKeyId.clone();
540
    else
541
      return null;
542
  }
543
 
544
  /**
545
   * Returns the subject public key criterion, or <code>null</code> if this
546
   * value is not set.
547
   *
548
   * @return The subject public key.
549
   */
550
  public PublicKey getSubjectPublicKey()
551
  {
552
    return subjectKey;
553
  }
554
 
555
  /**
556
   * Returns the public key algorithm ID that matching certificates must have,
557
   * or <code>null</code> if this criterion was not set.
558
   *
559
   * @return The public key algorithm ID.
560
   */
561
  public String getSubjectPublicKeyAlgID()
562
  {
563
    return String.valueOf(sigId);
564
  }
565
 
566
  /**
567
   * Match a certificate. This method will check the given certificate
568
   * against all the enabled criteria of this selector, and will return
569
   * <code>true</code> if the given certificate matches.
570
   *
571
   * @param certificate The certificate to check.
572
   * @return true if the certificate matches all criteria.
573
   */
574
  public boolean match(Certificate certificate)
575
  {
576
    if (!(certificate instanceof X509Certificate))
577
      return false;
578
    X509Certificate cert = (X509Certificate) certificate;
579
    if (this.cert != null)
580
      {
581
        try
582
          {
583
            byte[] e1 = this.cert.getEncoded();
584
            byte[] e2 = cert.getEncoded();
585
            if (!Arrays.equals(e1, e2))
586
              return false;
587
          }
588
        catch (CertificateEncodingException cee)
589
          {
590
            return false;
591
          }
592
      }
593
    if (serialNo != null)
594
      {
595
        if (!serialNo.equals(cert.getSerialNumber()))
596
          return false;
597
      }
598
    if (certValid != null)
599
      {
600
        try
601
          {
602
            cert.checkValidity(certValid);
603
          }
604
        catch (CertificateException ce)
605
          {
606
            return false;
607
          }
608
      }
609
    if (issuer != null)
610
      {
611
        if (!issuer.equals(cert.getIssuerX500Principal()))
612
          return false;
613
      }
614
    if (subject != null)
615
      {
616
        if (!subject.equals(cert.getSubjectX500Principal()))
617
          return false;
618
      }
619
    if (sigId != null)
620
      {
621
        if (!sigId.toString().equals(cert.getSigAlgOID()))
622
          return false;
623
      }
624
    if (subjectKeyId != null)
625
      {
626
        byte[] b = cert.getExtensionValue(SUBJECT_KEY_ID);
627
        if (!Arrays.equals(b, subjectKeyId))
628
          return false;
629
      }
630
    if (authKeyId != null)
631
      {
632
        byte[] b = cert.getExtensionValue(AUTH_KEY_ID);
633
        if (!Arrays.equals(b, authKeyId))
634
          return false;
635
      }
636
    if (keyUsage != null)
637
      {
638
        boolean[] b = cert.getKeyUsage();
639
        if (!Arrays.equals(b, keyUsage))
640
          return false;
641
      }
642
    if (basicConstraints >= 0)
643
      {
644
        if (cert.getBasicConstraints() != basicConstraints)
645
          return false;
646
      }
647
    if (keyPurposeSet != null)
648
      {
649
        List kp = null;
650
        try
651
          {
652
            kp = cert.getExtendedKeyUsage();
653
          }
654
        catch (CertificateParsingException cpe)
655
          {
656
            return false;
657
          }
658
        if (kp == null)
659
          return false;
660
        for (Iterator it = keyPurposeSet.iterator(); it.hasNext(); )
661
          {
662
            if (!kp.contains(it.next()))
663
              return false;
664
          }
665
      }
666
    if (altNames != null)
667
      {
668
        Collection<List<?>> an = null;
669
        try
670
          {
671
            an = cert.getSubjectAlternativeNames();
672
          }
673
        catch (CertificateParsingException cpe)
674
          {
675
            return false;
676
          }
677
        if (an == null)
678
          return false;
679
        int match = 0;
680
        for (GeneralName name : altNames)
681
          {
682
            for (List<?> list : an)
683
              {
684
                try
685
                  {
686
                    Integer id = (Integer) list.get(0);
687
                    Object val = list.get(1);
688
                    GeneralName n = null;
689
                    if (val instanceof String)
690
                      n = makeName(id, (String) val);
691
                    else if (val instanceof byte[])
692
                      {
693
                        n = new GeneralName(GeneralName.Kind.forTag(id),
694
                                            (byte[]) val);
695
                      }
696
                    else
697
                      continue;
698
                    if (name.equals(n))
699
                      match++;
700
                  }
701
                catch (Exception e)
702
                  {
703
                    continue;
704
                  }
705
              }
706
            if (match == 0 || (matchAllNames && match < altNames.size()))
707
              return false;
708
          }
709
      }
710
    if (nameConstraints != null)
711
      {
712
        byte[] nc = cert.getExtensionValue(NAME_CONSTRAINTS_ID);
713
        if (!Arrays.equals(nameConstraints, nc))
714
          return false;
715
      }
716
 
717
    if (policy != null)
718
      {
719
        CertificatePolicies policies = null;
720
        if (cert instanceof GnuPKIExtension)
721
          {
722
            policies = (CertificatePolicies)
723
              ((GnuPKIExtension) cert).getExtension(CertificatePolicies.ID).getValue();
724
          }
725
        else
726
          {
727
            byte[] policiesDer =
728
              cert.getExtensionValue(CertificatePolicies.ID.toString());
729
            try
730
              {
731
                policies = new CertificatePolicies(policiesDer);
732
              }
733
            catch (IOException ioe)
734
              {
735
                // ignored
736
              }
737
          }
738
 
739
        if (policies == null)
740
          return false;
741
        if (!policies.getPolicies().containsAll(policy))
742
          return false;
743
      }
744
 
745
    if (pathToNames != null)
746
      {
747
        NameConstraints nc = null;
748
        if (cert instanceof GnuPKIExtension)
749
          {
750
            Extension e =
751
              ((GnuPKIExtension) cert).getExtension(NameConstraints.ID);
752
            if (e != null)
753
              nc = (NameConstraints) e.getValue();
754
          }
755
        else
756
          {
757
            byte[] b = cert.getExtensionValue(NameConstraints.ID.toString());
758
            if (b != null)
759
              {
760
                try
761
                  {
762
                    nc = new NameConstraints(b);
763
                  }
764
                catch (IOException ioe)
765
                  {
766
                  }
767
              }
768
          }
769
 
770
        if (nc == null)
771
          return false;
772
 
773
        int match = 0;
774
        for (GeneralName name : pathToNames)
775
          {
776
            for (GeneralSubtree subtree : nc.permittedSubtrees())
777
              {
778
                if (name.equals(subtree.base()))
779
                  match++;
780
              }
781
          }
782
        if (match == 0 || (matchAllNames && match < pathToNames.size()))
783
          return false;
784
      }
785
 
786
    return true;
787
  }
788
 
789
  /**
790
   * Sets the authority key identifier criterion, or <code>null</code> to clear
791
   * this criterion. Note that the byte array is cloned to prevent modification.
792
   *
793
   * @param authKeyId The authority key identifier.
794
   */
795
  public void setAuthorityKeyIdentifier(byte[] authKeyId)
796
  {
797
    this.authKeyId = authKeyId != null ? (byte[]) authKeyId.clone() : null;
798
  }
799
 
800
  /**
801
   * Sets the basic constraints criterion. Specify -1 to clear this parameter.
802
   *
803
   * @param basicConstraints The new basic constraints value.
804
   */
805
  public void setBasicConstraints(int basicConstraints)
806
  {
807
    if (basicConstraints < -1)
808
      basicConstraints = -1;
809
    this.basicConstraints = basicConstraints;
810
  }
811
 
812
  /**
813
   * Sets the certificate criterion. If set, only certificates that are
814
   * equal to the certificate passed here will be accepted.
815
   *
816
   * @param cert The certificate.
817
   */
818
  public void setCertificate(X509Certificate cert)
819
  {
820
    this.cert = cert;
821
  }
822
 
823
  /**
824
   * Sets the date at which certificates must be valid. Specify
825
   * <code>null</code> to clear this criterion.
826
   *
827
   * @param certValid The certificate validity date.
828
   */
829
  public void setCertificateValid(Date certValid)
830
  {
831
    this.certValid = certValid != null ? (Date) certValid.clone() : null;
832
  }
833
 
834
  /**
835
   * Sets the extended key usage criterion, as a set of OID strings. Specify
836
   * <code>null</code> to clear this value.
837
   *
838
   * @param keyPurposeSet The set of key purpose OIDs.
839
   * @throws IOException If any element of the set is not a valid OID string.
840
   */
841
  public void setExtendedKeyUsage(Set<String> keyPurposeSet) throws IOException
842
  {
843
    if (keyPurposeSet == null)
844
      {
845
        this.keyPurposeSet = null;
846
        return;
847
      }
848
    Set<String> s = new HashSet<String>();
849
    for (Iterator it = keyPurposeSet.iterator(); it.hasNext(); )
850
      {
851
        Object o = it.next();
852
        if (!(o instanceof String))
853
          throw new IOException("not a string: " + o);
854
        try
855
          {
856
            OID oid = new OID((String) o);
857
            int[] comp = oid.getIDs();
858
            if (!checkOid(comp))
859
              throw new IOException("malformed OID: " + o);
860
          }
861
        catch (IllegalArgumentException iae)
862
          {
863
            IOException ioe = new IOException("malformed OID: " + o);
864
            ioe.initCause(iae);
865
            throw ioe;
866
          }
867
      }
868
    this.keyPurposeSet = s;
869
  }
870
 
871
  /**
872
   * Sets the issuer, specified as the DER encoding of the issuer's
873
   * distinguished name. Only certificates issued by this issuer will
874
   * be accepted.
875
   *
876
   * @param name The DER encoding of the issuer's distinguished name.
877
   * @throws IOException If the given name is incorrectly formatted.
878
   */
879
  public void setIssuer(byte[] name) throws IOException
880
  {
881
    if (name != null)
882
      {
883
        try
884
          {
885
            issuer = new X500Principal(name);
886
          }
887
        catch (IllegalArgumentException iae)
888
          {
889
            throw new IOException(iae.getMessage());
890
          }
891
      }
892
    else
893
      issuer = null;
894
  }
895
 
896
  /**
897
   * Sets the issuer, specified as a string representation of the issuer's
898
   * distinguished name. Only certificates issued by this issuer will
899
   * be accepted.
900
   *
901
   * @param name The string representation of the issuer's distinguished name.
902
   * @throws IOException If the given name is incorrectly formatted.
903
   */
904
  public void setIssuer(String name) throws IOException
905
  {
906
    if (name != null)
907
      {
908
        try
909
          {
910
            issuer = new X500Principal(name);
911
          }
912
        catch (IllegalArgumentException iae)
913
          {
914
            throw new IOException(iae.getMessage());
915
          }
916
      }
917
    else
918
      issuer = null;
919
  }
920
 
921
  /**
922
   * Sets the public key usage criterion. Specify <code>null</code> to clear
923
   * this value.
924
   *
925
   * @param keyUsage The public key usage.
926
   */
927
  public void setKeyUsage(boolean[] keyUsage)
928
  {
929
    this.keyUsage = keyUsage != null ? (boolean[]) keyUsage.clone() : null;
930
  }
931
 
932
  /**
933
   * Sets whether or not all subject alternative names must be matched.
934
   * If false, then a certificate will be considered a match if one
935
   * alternative name matches.
936
   *
937
   * @param matchAllNames Whether or not all alternative names must be
938
   *        matched.
939
   */
940
  public void setMatchAllSubjectAltNames(boolean matchAllNames)
941
  {
942
    this.matchAllNames = matchAllNames;
943
  }
944
 
945
  /**
946
   * Sets the name constraints criterion; specify <code>null</code> to
947
   * clear this criterion. Note that if non-null, the argument will be
948
   * cloned to prevent modification.
949
   *
950
   * @param nameConstraints The new name constraints.
951
   * @throws IOException If the argument is not a valid DER-encoded
952
   *         name constraints.
953
   */
954
  public void setNameConstraints(byte[] nameConstraints)
955
    throws IOException
956
  {
957
    // Check if the input is well-formed...
958
    new NameConstraints(nameConstraints);
959
 
960
    // But we just compare raw byte arrays.
961
    this.nameConstraints = nameConstraints != null
962
      ? (byte[]) nameConstraints.clone() : null;
963
  }
964
 
965
  /**
966
   * Sets the pathToNames criterion. The argument is a collection of
967
   * pairs, the first element of which is an {@link Integer} giving
968
   * the ID of the name, and the second element is either a {@link String}
969
   * or a byte array.
970
   *
971
   * See {@link #addPathToName(int, byte[])} and {@link #addPathToName(int, String)}
972
   * for how these arguments are handled.
973
   *
974
   * @param names The names.
975
   * @throws IOException If any argument is malformed.
976
   */
977
  public void setPathToNames(Collection<List<?>> names) throws IOException
978
  {
979
    if (names == null || names.size() == 0)
980
      {
981
        pathToNames = null;
982
      }
983
    else
984
      {
985
        pathToNames = new ArrayList<GeneralName>(names.size());
986
        for (List<?> name : names)
987
          {
988
            Integer id = (Integer) name.get(0);
989
            Object name2 = name.get(1);
990
            if (name2 instanceof String)
991
              addPathToName(id, (String) name2);
992
            else if (name2 instanceof byte[])
993
              addPathToName(id, (byte[]) name2);
994
            else
995
              throw new IOException("invalid name type: "
996
                                    + name2.getClass().getName());
997
          }
998
      }
999
  }
1000
 
1001
  /**
1002
   * Sets the certificate policy to match, or null if this criterion should
1003
   * not be checked. Each element if the set must be a dotted-decimal form
1004
   * of certificate policy object identifier.
1005
   *
1006
   * @param policy The policy to match.
1007
   * @throws IOException If some element of the policy is not a valid
1008
   *  policy extenison OID.
1009
   */
1010
  public void setPolicy(Set<String> policy) throws IOException
1011
  {
1012
    if (policy != null)
1013
      {
1014
        HashSet<OID> p = new HashSet<OID>(policy.size());
1015
        for (String s : policy)
1016
          {
1017
            try
1018
              {
1019
                OID oid = new OID(s);
1020
                int[] i = oid.getIDs();
1021
                if (!checkOid(i))
1022
                  throw new IOException("invalid OID");
1023
                p.add(oid);
1024
              }
1025
            catch (IOException ioe)
1026
              {
1027
                throw ioe;
1028
              }
1029
            catch (Exception x)
1030
              {
1031
                IOException ioe = new IOException("invalid OID");
1032
                ioe.initCause(x);
1033
                throw ioe;
1034
              }
1035
          }
1036
        this.policy = p;
1037
      }
1038
    else
1039
      this.policy = null;
1040
  }
1041
 
1042
  /**
1043
   * This method, and its related X.509 certificate extension &mdash; the
1044
   * private key usage period &mdash; is not supported under the Internet
1045
   * PKI for X.509 certificates (PKIX), described in RFC 3280. As such, this
1046
   * method is not supported either.
1047
   *
1048
   * <p>Do not use this method. It is not deprecated, as it is not deprecated
1049
   * in the Java standard, but it is basically a no-operation.
1050
   *
1051
   * @param UNUSED Is silently ignored.
1052
   */
1053
  public void setPrivateKeyValid(Date UNUSED)
1054
  {
1055
  }
1056
 
1057
  /**
1058
   * Sets the serial number of the desired certificate. Only certificates that
1059
   * contain this serial number are accepted.
1060
   *
1061
   * @param serialNo The serial number.
1062
   */
1063
  public void setSerialNumber(BigInteger serialNo)
1064
  {
1065
    this.serialNo = serialNo;
1066
  }
1067
 
1068
  /**
1069
   * Sets the subject, specified as the DER encoding of the subject's
1070
   * distinguished name. Only certificates with the given subject will
1071
   * be accepted.
1072
   *
1073
   * @param name The DER encoding of the subject's distinguished name.
1074
   * @throws IOException If the given name is incorrectly formatted.
1075
   */
1076
  public void setSubject(byte[] name) throws IOException
1077
  {
1078
    if (name != null)
1079
      {
1080
        try
1081
          {
1082
            subject = new X500Principal(name);
1083
          }
1084
        catch (IllegalArgumentException iae)
1085
          {
1086
            throw new IOException(iae.getMessage());
1087
          }
1088
      }
1089
    else
1090
      subject = null;
1091
  }
1092
 
1093
  /**
1094
   * Sets the subject, specified as a string representation of the
1095
   * subject's distinguished name. Only certificates with the given
1096
   * subject will be accepted.
1097
   *
1098
   * @param name The string representation of the subject's distinguished name.
1099
   * @throws IOException If the given name is incorrectly formatted.
1100
   */
1101
  public void setSubject(String name) throws IOException
1102
  {
1103
    if (name != null)
1104
      {
1105
        try
1106
          {
1107
            subject = new X500Principal(name);
1108
          }
1109
        catch (IllegalArgumentException iae)
1110
          {
1111
            throw new IOException(iae.getMessage());
1112
          }
1113
      }
1114
    else
1115
      subject = null;
1116
  }
1117
 
1118
  /**
1119
   * Sets the subject alternative names critertion. Each element of the
1120
   * argument must be a {@link java.util.List} that contains exactly two
1121
   * elements: the first an {@link Integer}, representing the type of
1122
   * name, and the second either a {@link String} or a byte array,
1123
   * representing the name itself.
1124
   *
1125
   * @param altNames The alternative names.
1126
   * @throws IOException If any element of the argument is invalid.
1127
   */
1128
  public void setSubjectAlternativeNames(Collection<List<?>> altNames)
1129
    throws IOException
1130
  {
1131
    if (altNames == null || altNames.isEmpty())
1132
      {
1133
        this.altNames = null;
1134
        return;
1135
      }
1136
    List<GeneralName> l = new ArrayList<GeneralName>(altNames.size());
1137
    for (List<?> list : altNames)
1138
      {
1139
        Integer id = (Integer) list.get(0);
1140
        Object value = list.get(1);
1141
        GeneralName name = null;
1142
        if (value instanceof String)
1143
          name = makeName(id, (String) value);
1144
        else if (value instanceof byte[])
1145
          name = new GeneralName(GeneralName.Kind.forTag(id), (byte[]) value);
1146
        else
1147
          throw new IOException("invalid name type: " + value.getClass().getName());
1148
        l.add(name);
1149
      }
1150
    this.altNames = l;
1151
  }
1152
 
1153
  /**
1154
   * Sets the subject key identifier criterion, or <code>null</code> to clear
1155
   * this criterion. Note that the byte array is cloned to prevent modification.
1156
   *
1157
   * @param subjectKeyId The subject key identifier.
1158
   */
1159
  public void setSubjectKeyIdentifier(byte[] subjectKeyId)
1160
  {
1161
    this.subjectKeyId = subjectKeyId != null ? (byte[]) subjectKeyId.clone() :
1162
      null;
1163
  }
1164
 
1165
  /**
1166
   * Sets the subject public key criterion as a DER-encoded key. Specify
1167
   * <code>null</code> to clear this value.
1168
   *
1169
   * @param key The DER-encoded key bytes.
1170
   * @throws IOException If the argument is not a valid DER-encoded key.
1171
   */
1172
  public void setSubjectPublicKey(byte[] key) throws IOException
1173
  {
1174
    if (key == null)
1175
      {
1176
        subjectKey = null;
1177
        subjectKeySpec = null;
1178
        return;
1179
      }
1180
    try
1181
      {
1182
        subjectKeySpec = new X509EncodedKeySpec(key);
1183
        KeyFactory enc = KeyFactory.getInstance("X.509");
1184
        subjectKey = enc.generatePublic(subjectKeySpec);
1185
      }
1186
    catch (Exception x)
1187
      {
1188
        subjectKey = null;
1189
        subjectKeySpec = null;
1190
        IOException ioe = new IOException(x.getMessage());
1191
        ioe.initCause(x);
1192
        throw ioe;
1193
      }
1194
  }
1195
 
1196
  /**
1197
   * Sets the subject public key criterion as an opaque representation.
1198
   * Specify <code>null</code> to clear this criterion.
1199
   *
1200
   * @param key The public key.
1201
   */
1202
  public void setSubjectPublicKey(PublicKey key)
1203
  {
1204
    this.subjectKey = key;
1205
    if (key == null)
1206
      {
1207
        subjectKeySpec = null;
1208
        return;
1209
      }
1210
    try
1211
      {
1212
        KeyFactory enc = KeyFactory.getInstance("X.509");
1213
        subjectKeySpec = (X509EncodedKeySpec)
1214
          enc.getKeySpec(key, X509EncodedKeySpec.class);
1215
      }
1216
    catch (Exception x)
1217
      {
1218
        subjectKey = null;
1219
        subjectKeySpec = null;
1220
      }
1221
  }
1222
 
1223
  /**
1224
   * Sets the public key algorithm ID that matching certificates must have.
1225
   * Specify <code>null</code> to clear this criterion.
1226
   *
1227
   * @param sigId The public key ID.
1228
   * @throws IOException If the specified ID is not a valid object identifier.
1229
   */
1230
  public void setSubjectPublicKeyAlgID(String sigId) throws IOException
1231
  {
1232
    if (sigId != null)
1233
      {
1234
        try
1235
          {
1236
            OID oid = new OID(sigId);
1237
            int[] comp = oid.getIDs();
1238
            if (!checkOid(comp))
1239
              throw new IOException("malformed OID: " + sigId);
1240
            this.sigId = oid;
1241
          }
1242
        catch (IllegalArgumentException iae)
1243
          {
1244
            IOException ioe = new IOException("malformed OID: " + sigId);
1245
            ioe.initCause(iae);
1246
            throw ioe;
1247
          }
1248
      }
1249
    else
1250
      this.sigId = null;
1251
  }
1252
 
1253
  public String toString()
1254
  {
1255
    CPStringBuilder str = new CPStringBuilder(X509CertSelector.class.getName());
1256
    String nl = SystemProperties.getProperty("line.separator");
1257
    String eol = ";" + nl;
1258
    str.append(" {").append(nl);
1259
    if (cert != null)
1260
      str.append("  certificate = ").append(cert).append(eol);
1261
    if (basicConstraints >= 0)
1262
      str.append("  basic constraints = ").append(basicConstraints).append(eol);
1263
    if (serialNo != null)
1264
      str.append("  serial number = ").append(serialNo).append(eol);
1265
    if (certValid != null)
1266
      str.append("  valid date = ").append(certValid).append(eol);
1267
    if (issuer != null)
1268
      str.append("  issuer = ").append(issuer).append(eol);
1269
    if (subject != null)
1270
      str.append("  subject = ").append(subject).append(eol);
1271
    if (sigId != null)
1272
      str.append("  signature OID = ").append(sigId).append(eol);
1273
    if (subjectKey != null)
1274
      str.append("  subject public key = ").append(subjectKey).append(eol);
1275
    if (subjectKeyId != null)
1276
      {
1277
        str.append("  subject key ID = ");
1278
        for (int i = 0; i < subjectKeyId.length; i++)
1279
          {
1280
            str.append(Character.forDigit((subjectKeyId[i] & 0xF0) >>> 8, 16));
1281
            str.append(Character.forDigit((subjectKeyId[i] & 0x0F), 16));
1282
            if (i < subjectKeyId.length - 1)
1283
              str.append(':');
1284
          }
1285
        str.append(eol);
1286
      }
1287
    if (authKeyId != null)
1288
      {
1289
        str.append("  authority key ID = ");
1290
        for (int i = 0; i < authKeyId.length; i++)
1291
          {
1292
            str.append(Character.forDigit((authKeyId[i] & 0xF0) >>> 8, 16));
1293
            str.append(Character.forDigit((authKeyId[i] & 0x0F), 16));
1294
            if (i < authKeyId.length - 1)
1295
              str.append(':');
1296
          }
1297
        str.append(eol);
1298
      }
1299
    if (keyUsage != null)
1300
      {
1301
        str.append("  key usage = ");
1302
        for (int i = 0; i < keyUsage.length; i++)
1303
          str.append(keyUsage[i] ? '1' : '0');
1304
        str.append(eol);
1305
      }
1306
    if (keyPurposeSet != null)
1307
      str.append("  key purpose = ").append(keyPurposeSet).append(eol);
1308
    if (altNames != null)
1309
      str.append("  alternative names = ").append(altNames).append(eol);
1310
    if (nameConstraints != null)
1311
      str.append("  name constraints = <blob of data>").append(eol);
1312
    if (policy != null)
1313
      str.append("  policy = ").append(policy).append(eol);
1314
    if (pathToNames != null)
1315
      str.append("  pathToNames = ").append(pathToNames).append(eol);
1316
    str.append("}").append(nl);
1317
    return str.toString();
1318
  }
1319
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.