KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > java > security > cert > CertPath


1 /*
2  * @(#)CertPath.java 1.9 03/12/19
3  *
4  * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
5  * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
6  */

7
8 package java.security.cert;
9
10 import java.io.ByteArrayInputStream JavaDoc;
11 import java.io.NotSerializableException JavaDoc;
12 import java.io.ObjectStreamException JavaDoc;
13 import java.io.Serializable JavaDoc;
14 import java.util.Iterator JavaDoc;
15 import java.util.List JavaDoc;
16
17 /**
18  * An immutable sequence of certificates (a certification path).
19  * <p>
20  * This is an abstract class that defines the methods common to all
21  * <code>CertPath</code>s. Subclasses can handle different kinds of
22  * certificates (X.509, PGP, etc.).
23  * <p>
24  * All <code>CertPath</code> objects have a type, a list of
25  * <code>Certificate</code>s, and one or more supported encodings. Because the
26  * <code>CertPath</code> class is immutable, a <code>CertPath</code> cannot
27  * change in any externally visible way after being constructed. This
28  * stipulation applies to all public fields and methods of this class and any
29  * added or overridden by subclasses.
30  * <p>
31  * The type is a <code>String</code> that identifies the type of
32  * <code>Certificate</code>s in the certification path. For each
33  * certificate <code>cert</code> in a certification path <code>certPath</code>,
34  * <code>cert.getType().equals(certPath.getType())</code> must be
35  * <code>true</code>.
36  * <p>
37  * The list of <code>Certificate</code>s is an ordered <code>List</code> of
38  * zero or more <code>Certificate</code>s. This <code>List</code> and all
39  * of the <code>Certificate</code>s contained in it must be immutable.
40  * <p>
41  * Each <code>CertPath</code> object must support one or more encodings
42  * so that the object can be translated into a byte array for storage or
43  * transmission to other parties. Preferably, these encodings should be
44  * well-documented standards (such as PKCS#7). One of the encodings supported
45  * by a <code>CertPath</code> is considered the default encoding. This
46  * encoding is used if no encoding is explicitly requested (for the
47  * {@link #getEncoded() getEncoded()} method, for instance).
48  * <p>
49  * All <code>CertPath</code> objects are also <code>Serializable</code>.
50  * <code>CertPath</code> objects are resolved into an alternate
51  * {@link CertPathRep CertPathRep} object during serialization. This allows
52  * a <code>CertPath</code> object to be serialized into an equivalent
53  * representation regardless of its underlying implementation.
54  * <p>
55  * <code>CertPath</code> objects can be created with a
56  * <code>CertificateFactory</code> or they can be returned by other classes,
57  * such as a <code>CertPathBuilder</code>.
58  * <p>
59  * By convention, X.509 <code>CertPath</code>s (consisting of
60  * <code>X509Certificate</code>s), are ordered starting with the target
61  * certificate and ending with a certificate issued by the trust anchor. That
62  * is, the issuer of one certificate is the subject of the following one. The
63  * certificate representing the {@link TrustAnchor TrustAnchor} should not be
64  * included in the certification path. Unvalidated X.509 <code>CertPath</code>s
65  * may not follow these conventions. PKIX <code>CertPathValidator</code>s will
66  * detect any departure from these conventions that cause the certification
67  * path to be invalid and throw a <code>CertPathValidatorException</code>.
68  * <p>
69  * <b>Concurrent Access</b>
70  * <p>
71  * All <code>CertPath</code> objects must be thread-safe. That is, multiple
72  * threads may concurrently invoke the methods defined in this class on a
73  * single <code>CertPath</code> object (or more than one) with no
74  * ill effects. This is also true for the <code>List</code> returned by
75  * <code>CertPath.getCertificates</code>.
76  * <p>
77  * Requiring <code>CertPath</code> objects to be immutable and thread-safe
78  * allows them to be passed around to various pieces of code without worrying
79  * about coordinating access. Providing this thread-safety is
80  * generally not difficult, since the <code>CertPath</code> and
81  * <code>List</code> objects in question are immutable.
82  *
83  * @see CertificateFactory
84  * @see CertPathBuilder
85  *
86  * @version 1.9 12/19/03
87  * @author Yassir Elley
88  * @since 1.4
89  */

90 public abstract class CertPath implements Serializable JavaDoc {
91
92     private static final long serialVersionUID = 6068470306649138683L;
93    
94     private String JavaDoc type; // the type of certificates in this chain
95

96     /**
97      * Creates a <code>CertPath</code> of the specified type.
98      * <p>
99      * This constructor is protected because most users should use a
100      * <code>CertificateFactory</code> to create <code>CertPath</code>s.
101      *
102      * @param type the standard name of the type of
103      * <code>Certificate</code>s in this path
104      */

105     protected CertPath(String JavaDoc type) {
106         this.type = type;
107     }
108
109     /**
110      * Returns the type of <code>Certificate</code>s in this certification
111      * path. This is the same string that would be returned by
112      * {@link java.security.cert.Certificate#getType() cert.getType()}
113      * for all <code>Certificate</code>s in the certification path.
114      *
115      * @return the type of <code>Certificate</code>s in this certification
116      * path (never null)
117      */

118     public String JavaDoc getType() {
119         return type;
120     }
121
122     /**
123      * Returns an iteration of the encodings supported by this certification
124      * path, with the default encoding first. Attempts to modify the returned
125      * <code>Iterator</code> via its <code>remove</code> method result in an
126      * <code>UnsupportedOperationException</code>.
127      *
128      * @return an <code>Iterator</code> over the names of the supported
129      * encodings (as Strings)
130      */

131     public abstract Iterator JavaDoc<String JavaDoc> getEncodings();
132
133     /**
134      * Compares this certification path for equality with the specified
135      * object. Two <code>CertPath</code>s are equal if and only if their
136      * types are equal and their certificate <code>List</code>s (and by
137      * implication the <code>Certificate</code>s in those <code>List</code>s)
138      * are equal. A <code>CertPath</code> is never equal to an object that is
139      * not a <code>CertPath</code>.
140      * <p>
141      * This algorithm is implemented by this method. If it is overridden,
142      * the behavior specified here must be maintained.
143      *
144      * @param other the object to test for equality with this certification path
145      * @return true if the specified object is equal to this certification path,
146      * false otherwise
147      */

148     public boolean equals(Object JavaDoc other) {
149         if (this == other)
150             return true;
151     
152         if (! (other instanceof CertPath JavaDoc))
153             return false;
154
155         CertPath JavaDoc otherCP = (CertPath JavaDoc) other;
156         if (! otherCP.getType().equals(type))
157             return false;
158
159         List JavaDoc thisCertList = this.getCertificates();
160         List JavaDoc otherCertList = otherCP.getCertificates();
161         return(thisCertList.equals(otherCertList));
162     }
163
164     /**
165      * Returns the hashcode for this certification path. The hash code of
166      * a certification path is defined to be the result of the following
167      * calculation:
168      * <pre><code>
169      * hashCode = path.getType().hashCode();
170      * hashCode = 31*hashCode + path.getCertificates().hashCode();
171      * </code></pre>
172      * This ensures that <code>path1.equals(path2)</code> implies that
173      * <code>path1.hashCode()==path2.hashCode()</code> for any two certification
174      * paths, <code>path1</code> and <code>path2</code>, as required by the
175      * general contract of <code>Object.hashCode</code>.
176      *
177      * @return the hashcode value for this certification path
178      */

179     public int hashCode() {
180         int hashCode = type.hashCode();
181         hashCode = 31*hashCode + getCertificates().hashCode();
182         return hashCode;
183     }
184
185     /**
186      * Returns a string representation of this certification path.
187      * This calls the <code>toString</code> method on each of the
188      * <code>Certificate</code>s in the path.
189      *
190      * @return a string representation of this certification path
191      */

192     public String JavaDoc toString() {
193         StringBuffer JavaDoc sb = new StringBuffer JavaDoc();
194         Iterator JavaDoc stringIterator = getCertificates().iterator();
195
196         sb.append("\n" + type + " Cert Path: length = "
197         + getCertificates().size() + ".\n");
198         sb.append("[\n");
199         int i = 1;
200         while (stringIterator.hasNext()) {
201             sb.append("=========================================="
202         + "===============Certificate " + i + " start.\n");
203             Certificate JavaDoc stringCert = (Certificate JavaDoc) stringIterator.next();
204             sb.append(stringCert.toString());
205             sb.append("\n========================================"
206         + "=================Certificate " + i + " end.\n\n\n");
207             i++;
208         }
209
210         sb.append("\n]");
211         return sb.toString();
212     }
213
214     /**
215      * Returns the encoded form of this certification path, using the default
216      * encoding.
217      *
218      * @return the encoded bytes
219      * @exception CertificateEncodingException if an encoding error occurs
220      */

221     public abstract byte[] getEncoded()
222         throws CertificateEncodingException JavaDoc;
223
224     /**
225      * Returns the encoded form of this certification path, using the
226      * specified encoding.
227      *
228      * @param encoding the name of the encoding to use
229      * @return the encoded bytes
230      * @exception CertificateEncodingException if an encoding error occurs or
231      * the encoding requested is not supported
232      */

233     public abstract byte[] getEncoded(String JavaDoc encoding)
234         throws CertificateEncodingException JavaDoc;
235
236     /**
237      * Returns the list of certificates in this certification path.
238      * The <code>List</code> returned must be immutable and thread-safe.
239      *
240      * @return an immutable <code>List</code> of <code>Certificate</code>s
241      * (may be empty, but not null)
242      */

243     public abstract List JavaDoc<? extends Certificate JavaDoc> getCertificates();
244
245     /**
246      * Replaces the <code>CertPath</code> to be serialized with a
247      * <code>CertPathRep</code> object.
248      *
249      * @return the <code>CertPathRep</code> to be serialized
250      *
251      * @throws ObjectStreamException if a <code>CertPathRep</code> object
252      * representing this certification path could not be created
253      */

254     protected Object JavaDoc writeReplace() throws ObjectStreamException JavaDoc {
255         try {
256             return new CertPathRep(type, getEncoded());
257         } catch (CertificateException JavaDoc ce) {
258         NotSerializableException JavaDoc nse =
259         new NotSerializableException JavaDoc
260             ("java.security.cert.CertPath: " + type);
261         nse.initCause(ce);
262         throw nse;
263         }
264     }
265
266     /**
267      * Alternate <code>CertPath</code> class for serialization.
268      */

269     protected static class CertPathRep implements Serializable JavaDoc {
270
271     private static final long serialVersionUID = 3015633072427920915L;
272
273         /** The Certificate type */
274         private String JavaDoc type;
275         /** The encoded form of the cert path */
276         private byte[] data;
277
278         /**
279          * Creates a <code>CertPathRep</code> with the specified
280          * type and encoded form of a certification path.
281          *
282          * @param type the standard name of a <code>CertPath</code> type
283          * @param data the encoded form of the certification path
284          */

285         protected CertPathRep(String JavaDoc type, byte[] data) {
286             this.type = type;
287             this.data = data;
288         }
289
290         /**
291          * Returns a <code>CertPath</code> constructed from the type and data.
292          *
293          * @return the resolved <code>CertPath</code> object
294          *
295          * @throws ObjectStreamException if a <code>CertPath</code> could not
296          * be constructed
297          */

298         protected Object JavaDoc readResolve() throws ObjectStreamException JavaDoc {
299             try {
300                 CertificateFactory JavaDoc cf = CertificateFactory.getInstance(type);
301                 return cf.generateCertPath(new ByteArrayInputStream JavaDoc(data));
302             } catch (CertificateException JavaDoc ce) {
303             NotSerializableException JavaDoc nse =
304             new NotSerializableException JavaDoc
305                 ("java.security.cert.CertPath: " + type);
306             nse.initCause(ce);
307             throw nse;
308             }
309         }
310     }
311 }
312
Popular Tags